add destructive outlines, more action usage and state fixups in GUI
[ardour.git] / libs / ardour / session.cc
1 /*
2     Copyright (C) 1999-2004 Paul Davis 
3
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.
8
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.
13
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.
17
18     $Id$
19 */
20
21 #include <algorithm>
22 #include <string>
23 #include <vector>
24 #include <sstream>
25 #include <fstream>
26 #include <cstdio> /* sprintf(3) ... grrr */
27 #include <cmath>
28 #include <cerrno>
29 #include <unistd.h>
30 #include <limits.h>
31
32 #include <sigc++/bind.h>
33 #include <sigc++/retype.h>
34
35 #include <pbd/error.h>
36 #include <pbd/lockmonitor.h>
37 #include <pbd/pathscanner.h>
38 #include <pbd/stl_delete.h>
39 #include <pbd/basename.h>
40 #include <pbd/dirname.h>
41
42 #include <ardour/audioengine.h>
43 #include <ardour/configuration.h>
44 #include <ardour/session.h>
45 #include <ardour/diskstream.h>
46 #include <ardour/utils.h>
47 #include <ardour/audioplaylist.h>
48 #include <ardour/audioregion.h>
49 #include <ardour/source.h>
50 #include <ardour/filesource.h>
51 #include <ardour/destructive_filesource.h>
52 #include <ardour/sndfilesource.h>
53 #include <ardour/auditioner.h>
54 #include <ardour/recent_sessions.h>
55 #include <ardour/redirect.h>
56 #include <ardour/send.h>
57 #include <ardour/insert.h>
58 #include <ardour/connection.h>
59 #include <ardour/slave.h>
60 #include <ardour/tempo.h>
61 #include <ardour/audio_track.h>
62 #include <ardour/cycle_timer.h>
63 #include <ardour/named_selection.h>
64 #include <ardour/crossfade.h>
65 #include <ardour/playlist.h>
66 #include <ardour/click.h>
67 #include <ardour/timestamps.h>
68
69 #include "i18n.h"
70
71 using namespace std;
72 using namespace ARDOUR;
73 //using namespace sigc;
74
75 const char* Session::_template_suffix = X_(".template");
76 const char* Session::_statefile_suffix = X_(".ardour");
77 const char* Session::_pending_suffix = X_(".pending");
78 const char* Session::sound_dir_name = X_("sounds");
79 const char* Session::peak_dir_name = X_("peaks");
80 const char* Session::dead_sound_dir_name = X_("dead_sounds");
81
82 Session::compute_peak_t                         Session::compute_peak                   = 0;
83 Session::apply_gain_to_buffer_t         Session::apply_gain_to_buffer   = 0;
84 Session::mix_buffers_with_gain_t        Session::mix_buffers_with_gain  = 0;
85 Session::mix_buffers_no_gain_t          Session::mix_buffers_no_gain    = 0;
86
87 sigc::signal<int> Session::AskAboutPendingState;
88
89 int
90 Session::find_session (string str, string& path, string& snapshot, bool& isnew)
91 {
92         struct stat statbuf;
93         char buf[PATH_MAX+1];
94
95         isnew = false;
96
97         if (!realpath (str.c_str(), buf) && (errno != ENOENT && errno != ENOTDIR)) {
98                 error << string_compose (_("Could not resolve path: %1 (%2)"), buf, strerror(errno)) << endmsg;
99                 return -1;
100         }
101
102         str = buf;
103         
104         /* check to see if it exists, and what it is */
105
106         if (stat (str.c_str(), &statbuf)) {
107                 if (errno == ENOENT) {
108                         isnew = true;
109                 } else {
110                         error << string_compose (_("cannot check session path %1 (%2)"), str, strerror (errno))
111                               << endmsg;
112                         return -1;
113                 }
114         }
115
116         if (!isnew) {
117
118                 /* it exists, so it must either be the name
119                    of the directory, or the name of the statefile
120                    within it.
121                 */
122
123                 if (S_ISDIR (statbuf.st_mode)) {
124
125                         string::size_type slash = str.find_last_of ('/');
126                 
127                         if (slash == string::npos) {
128                                 
129                                 /* a subdirectory of cwd, so statefile should be ... */
130
131                                 string tmp;
132                                 tmp = str;
133                                 tmp += '/';
134                                 tmp += str;
135                                 tmp += _statefile_suffix;
136
137                                 /* is it there ? */
138                                 
139                                 if (stat (tmp.c_str(), &statbuf)) {
140                                         error << string_compose (_("cannot check statefile %1 (%2)"), tmp, strerror (errno))
141                                               << endmsg;
142                                         return -1;
143                                 }
144
145                                 path = str;
146                                 snapshot = str;
147
148                         } else {
149
150                                 /* some directory someplace in the filesystem.
151                                    the snapshot name is the directory name
152                                    itself.
153                                 */
154
155                                 path = str;
156                                 snapshot = str.substr (slash+1);
157                                         
158                         }
159
160                 } else if (S_ISREG (statbuf.st_mode)) {
161                         
162                         string::size_type slash = str.find_last_of ('/');
163                         string::size_type suffix;
164
165                         /* remove the suffix */
166                         
167                         if (slash != string::npos) {
168                                 snapshot = str.substr (slash+1);
169                         } else {
170                                 snapshot = str;
171                         }
172
173                         suffix = snapshot.find (_statefile_suffix);
174                         
175                         if (suffix == string::npos) {
176                                 error << string_compose (_("%1 is not an Ardour snapshot file"), str) << endmsg;
177                                 return -1;
178                         }
179
180                         /* remove suffix */
181
182                         snapshot = snapshot.substr (0, suffix);
183                         
184                         if (slash == string::npos) {
185                                 
186                                 /* we must be in the directory where the 
187                                    statefile lives. get it using cwd().
188                                 */
189
190                                 char cwd[PATH_MAX+1];
191
192                                 if (getcwd (cwd, sizeof (cwd)) == 0) {
193                                         error << string_compose (_("cannot determine current working directory (%1)"), strerror (errno))
194                                               << endmsg;
195                                         return -1;
196                                 }
197
198                                 path = cwd;
199
200                         } else {
201
202                                 /* full path to the statefile */
203
204                                 path = str.substr (0, slash);
205                         }
206                                 
207                 } else {
208
209                         /* what type of file is it? */
210                         error << string_compose (_("unknown file type for session %1"), str) << endmsg;
211                         return -1;
212                 }
213
214         } else {
215
216                 /* its the name of a new directory. get the name
217                    as "dirname" does.
218                 */
219
220                 string::size_type slash = str.find_last_of ('/');
221
222                 if (slash == string::npos) {
223                         
224                         /* no slash, just use the name, but clean it up */
225                         
226                         path = legalize_for_path (str);
227                         snapshot = path;
228                         
229                 } else {
230                         
231                         path = str;
232                         snapshot = str.substr (slash+1);
233                 }
234         }
235
236         return 0;
237 }
238
239 Session::Session (AudioEngine &eng,
240                   string fullpath,
241                   string snapshot_name,
242                   string* mix_template)
243
244         : _engine (eng),
245           _mmc_port (default_mmc_port),
246           _mtc_port (default_mtc_port),
247           _midi_port (default_midi_port),
248           pending_events (2048),
249           midi_requests (128), // the size of this should match the midi request pool size
250           main_outs (0)
251 {
252         bool new_session;
253
254         cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << endl;
255
256         n_physical_outputs = _engine.n_physical_outputs();
257         n_physical_inputs =  _engine.n_physical_inputs();
258
259         first_stage_init (fullpath, snapshot_name);
260         
261         if (create (new_session, mix_template, _engine.frame_rate() * 60 * 5)) {
262                 throw failed_constructor ();
263         }
264         
265         if (second_stage_init (new_session)) {
266                 throw failed_constructor ();
267         }
268         
269         store_recent_sessions(_name, _path);
270         
271         bool was_dirty = dirty();
272
273         _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
274
275         if (was_dirty) {
276                 DirtyChanged (); /* EMIT SIGNAL */
277         }
278 }
279
280 Session::Session (AudioEngine &eng,
281                   string fullpath,
282                   string snapshot_name,
283                   AutoConnectOption input_ac,
284                   AutoConnectOption output_ac,
285                   uint32_t control_out_channels,
286                   uint32_t master_out_channels,
287                   uint32_t requested_physical_in,
288                   uint32_t requested_physical_out,
289                   jack_nframes_t initial_length)
290
291         : _engine (eng),
292           _mmc_port (default_mmc_port),
293           _mtc_port (default_mtc_port),
294           _midi_port (default_midi_port),
295           pending_events (2048),
296           midi_requests (16),
297           main_outs (0)
298
299 {
300         bool new_session;
301
302         cerr << "Loading session " << fullpath << " using snapshot " << snapshot_name << endl;
303
304         n_physical_outputs = max (requested_physical_out, _engine.n_physical_outputs());
305         n_physical_inputs = max (requested_physical_in, _engine.n_physical_inputs());
306
307         first_stage_init (fullpath, snapshot_name);
308         
309         if (create (new_session, 0, initial_length)) {
310                 throw failed_constructor ();
311         }
312
313         if (control_out_channels) {
314                 Route* r;
315                 r = new Route (*this, _("monitor"), -1, control_out_channels, -1, control_out_channels, Route::ControlOut);
316                 add_route (r);
317                 _control_out = r;
318         }
319
320         if (master_out_channels) {
321                 Route* r;
322                 r = new Route (*this, _("master"), -1, master_out_channels, -1, master_out_channels, Route::MasterOut);
323                 add_route (r);
324                 _master_out = r;
325         } else {
326                 /* prohibit auto-connect to master, because there isn't one */
327                 output_ac = AutoConnectOption (output_ac & ~AutoConnectMaster);
328         }
329
330         input_auto_connect = input_ac;
331         output_auto_connect = output_ac;
332
333         if (second_stage_init (new_session)) {
334                 throw failed_constructor ();
335         }
336         
337         store_recent_sessions(_name, _path);
338         
339         bool was_dirty = dirty ();
340
341         _state_of_the_state = StateOfTheState (_state_of_the_state & ~Dirty);
342
343         if (was_dirty) {
344                 DirtyChanged (); /* EMIT SIGNAL */
345         }
346 }
347
348 Session::~Session ()
349 {
350         /* if we got to here, leaving pending capture state around
351            is a mistake.
352         */
353
354         remove_pending_capture_state ();
355
356         _state_of_the_state = StateOfTheState (CannotSave|Deletion);
357         _engine.remove_session ();
358         
359         going_away (); /* EMIT SIGNAL */
360         
361         terminate_butler_thread ();
362         terminate_midi_thread ();
363         terminate_feedback ();
364         
365         if (click_data && click_data != default_click) {
366                 delete [] click_data;
367         }
368
369         if (click_emphasis_data && click_emphasis_data != default_click_emphasis) {
370                 delete [] click_emphasis_data;
371         }
372
373         clear_clicks ();
374
375         if (_click_io) {
376                 delete _click_io;
377         }
378
379
380         if (auditioner) {
381                 delete auditioner;
382         }
383
384         for (vector<Sample*>::iterator i = _passthru_buffers.begin(); i != _passthru_buffers.end(); ++i) {
385                 free(*i);
386         }
387
388         for (vector<Sample*>::iterator i = _silent_buffers.begin(); i != _silent_buffers.end(); ++i) {
389                 free(*i);
390         }
391
392 #undef TRACK_DESTRUCTION
393 #ifdef TRACK_DESTRUCTION
394         cerr << "delete named selections\n";
395 #endif /* TRACK_DESTRUCTION */
396         for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ) {
397                 NamedSelectionList::iterator tmp;
398
399                 tmp = i;
400                 ++tmp;
401
402                 delete *i;
403                 i = tmp;
404         }
405
406 #ifdef TRACK_DESTRUCTION
407         cerr << "delete playlists\n";
408 #endif /* TRACK_DESTRUCTION */
409         for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ) {
410                 PlaylistList::iterator tmp;
411
412                 tmp = i;
413                 ++tmp;
414
415                 delete *i;
416                 
417                 i = tmp;
418         }
419
420 #ifdef TRACK_DESTRUCTION
421         cerr << "delete audio regions\n";
422 #endif /* TRACK_DESTRUCTION */
423         for (AudioRegionList::iterator i = audio_regions.begin(); i != audio_regions.end(); ) {
424                 AudioRegionList::iterator tmp;
425
426                 tmp =i;
427                 ++tmp;
428
429                 delete (*i).second;
430
431                 i = tmp;
432         }
433         
434 #ifdef TRACK_DESTRUCTION
435         cerr << "delete routes\n";
436 #endif /* TRACK_DESTRUCTION */
437         for (RouteList::iterator i = routes.begin(); i != routes.end(); ) {
438                 RouteList::iterator tmp;
439                 tmp = i;
440                 ++tmp;
441                 delete *i;
442                 i = tmp;
443         }
444
445 #ifdef TRACK_DESTRUCTION
446         cerr << "delete diskstreams\n";
447 #endif /* TRACK_DESTRUCTION */
448         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ) {
449                 DiskStreamList::iterator tmp;
450
451                 tmp = i;
452                 ++tmp;
453
454                 delete *i;
455
456                 i = tmp;
457         }
458
459 #ifdef TRACK_DESTRUCTION
460         cerr << "delete sources\n";
461 #endif /* TRACK_DESTRUCTION */
462         for (SourceList::iterator i = sources.begin(); i != sources.end(); ) {
463                 SourceList::iterator tmp;
464
465                 tmp = i;
466                 ++tmp;
467
468                 delete (*i).second;
469
470                 i = tmp;
471         }
472
473 #ifdef TRACK_DESTRUCTION
474         cerr << "delete mix groups\n";
475 #endif /* TRACK_DESTRUCTION */
476         for (list<RouteGroup *>::iterator i = mix_groups.begin(); i != mix_groups.end(); ) {
477                 list<RouteGroup*>::iterator tmp;
478
479                 tmp = i;
480                 ++tmp;
481
482                 delete *i;
483
484                 i = tmp;
485         }
486
487 #ifdef TRACK_DESTRUCTION
488         cerr << "delete edit groups\n";
489 #endif /* TRACK_DESTRUCTION */
490         for (list<RouteGroup *>::iterator i = edit_groups.begin(); i != edit_groups.end(); ) {
491                 list<RouteGroup*>::iterator tmp;
492                 
493                 tmp = i;
494                 ++tmp;
495
496                 delete *i;
497
498                 i = tmp;
499         }
500         
501 #ifdef TRACK_DESTRUCTION
502         cerr << "delete connections\n";
503 #endif /* TRACK_DESTRUCTION */
504         for (ConnectionList::iterator i = _connections.begin(); i != _connections.end(); ) {
505                 ConnectionList::iterator tmp;
506
507                 tmp = i;
508                 ++tmp;
509
510                 delete *i;
511
512                 i = tmp;
513         }
514
515         if (butler_mixdown_buffer) {
516                 delete [] butler_mixdown_buffer;
517         }
518
519         if (butler_gain_buffer) {
520                 delete [] butler_gain_buffer;
521         }
522
523         Crossfade::set_buffer_size (0);
524
525         if (mmc) {
526                 delete mmc;
527         }
528
529         if (state_tree) {
530                 delete state_tree;
531         }
532 }
533
534 void
535 Session::set_worst_io_latencies (bool take_lock)
536 {
537         _worst_output_latency = 0;
538         _worst_input_latency = 0;
539
540         if (!_engine.connected()) {
541                 return;
542         }
543
544         if (take_lock) {
545                 route_lock.read_lock ();
546         }
547         
548         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
549                 _worst_output_latency = max (_worst_output_latency, (*i)->output_latency());
550                 _worst_input_latency = max (_worst_input_latency, (*i)->input_latency());
551         }
552
553         if (take_lock) {
554                 route_lock.unlock ();
555         }
556 }
557
558 void
559 Session::when_engine_running ()
560 {
561         string first_physical_output;
562
563         /* we don't want to run execute this again */
564
565         first_time_running.disconnect ();
566
567         set_block_size (_engine.frames_per_cycle());
568         set_frame_rate (_engine.frame_rate());
569
570         /* every time we reconnect, recompute worst case output latencies */
571
572         _engine.Running.connect (sigc::bind (mem_fun (*this, &Session::set_worst_io_latencies), true));
573
574         if (synced_to_jack()) {
575                 _engine.transport_stop ();
576         }
577
578         if (Config->get_jack_time_master()) {
579                 _engine.transport_locate (_transport_frame);
580         }
581
582         _clicking = false;
583
584         try {
585                 XMLNode* child = 0;
586                 
587                 _click_io = new ClickIO (*this, "click", 0, 0, -1, -1);
588
589                 if (state_tree && (child = find_named_node (*state_tree->root(), "Click")) != 0) {
590
591                         /* existing state for Click */
592                         
593                         if (_click_io->set_state (*child->children().front()) == 0) {
594                                 
595                                 _clicking = click_requested;
596
597                         } else {
598
599                                 error << _("could not setup Click I/O") << endmsg;
600                                 _clicking = false;
601                         }
602
603                 } else {
604                         
605                         /* default state for Click */
606
607                         first_physical_output = _engine.get_nth_physical_output (0);
608                         
609                         if (first_physical_output.length()) {
610                                 if (_click_io->add_output_port (first_physical_output, this)) {
611                                         // relax, even though its an error
612                                 } else {
613                                         _clicking = click_requested;
614                                 }
615                         }
616                 }
617         }
618
619         catch (failed_constructor& err) {
620                 error << _("cannot setup Click I/O") << endmsg;
621         }
622
623         set_worst_io_latencies (true);
624
625         if (_clicking) {
626                  ControlChanged (Clicking); /* EMIT SIGNAL */
627         }
628
629         if (auditioner == 0) {
630
631                 /* we delay creating the auditioner till now because
632                    it makes its own connections to ports named
633                    in the ARDOUR_RC config file. the engine has
634                    to be running for this to work.
635                 */
636
637                 try {
638                         auditioner = new Auditioner (*this);
639                 }
640
641                 catch (failed_constructor& err) {
642                         warning << _("cannot create Auditioner: no auditioning of regions possible") << endmsg;
643                 }
644         }
645
646         /* Create a set of Connection objects that map
647            to the physical outputs currently available
648         */
649
650         /* ONE: MONO */
651
652         for (uint32_t np = 0; np < n_physical_outputs; ++np) {
653                 char buf[32];
654                 snprintf (buf, sizeof (buf), _("out %" PRIu32), np+1);
655
656                 Connection* c = new OutputConnection (buf, true);
657
658                 c->add_port ();
659                 c->add_connection (0, _engine.get_nth_physical_output (np));
660
661                 add_connection (c);
662         }
663
664         for (uint32_t np = 0; np < n_physical_inputs; ++np) {
665                 char buf[32];
666                 snprintf (buf, sizeof (buf), _("in %" PRIu32), np+1);
667
668                 Connection* c = new InputConnection (buf, true);
669
670                 c->add_port ();
671                 c->add_connection (0, _engine.get_nth_physical_input (np));
672
673                 add_connection (c);
674         }
675
676         /* TWO: STEREO */
677
678         for (uint32_t np = 0; np < n_physical_outputs; np +=2) {
679                 char buf[32];
680                 snprintf (buf, sizeof (buf), _("out %" PRIu32 "+%" PRIu32), np+1, np+2);
681
682                 Connection* c = new OutputConnection (buf, true);
683
684                 c->add_port ();
685                 c->add_port ();
686                 c->add_connection (0, _engine.get_nth_physical_output (np));
687                 c->add_connection (1, _engine.get_nth_physical_output (np+1));
688
689                 add_connection (c);
690         }
691
692         for (uint32_t np = 0; np < n_physical_inputs; np +=2) {
693                 char buf[32];
694                 snprintf (buf, sizeof (buf), _("in %" PRIu32 "+%" PRIu32), np+1, np+2);
695
696                 Connection* c = new InputConnection (buf, true);
697
698                 c->add_port ();
699                 c->add_port ();
700                 c->add_connection (0, _engine.get_nth_physical_input (np));
701                 c->add_connection (1, _engine.get_nth_physical_input (np+1));
702
703                 add_connection (c);
704         }
705
706         /* THREE MASTER */
707
708         if (_master_out) {
709
710                 /* create master/control ports */
711                 
712                 if (_master_out) {
713                         uint32_t n;
714
715                         /* force the master to ignore any later call to this */
716                         
717                         if (_master_out->pending_state_node) {
718                                 _master_out->ports_became_legal();
719                         }
720
721                         /* no panner resets till we are through */
722                         
723                         _master_out->defer_pan_reset ();
724                         
725                         while ((int) _master_out->n_inputs() < _master_out->input_maximum()) {
726                                 if (_master_out->add_input_port ("", this)) {
727                                         error << _("cannot setup master inputs") 
728                                               << endmsg;
729                                         break;
730                                 }
731                         }
732                         n = 0;
733                         while ((int) _master_out->n_outputs() < _master_out->output_maximum()) {
734                                 if (_master_out->add_output_port (_engine.get_nth_physical_output (n), this)) {
735                                         error << _("cannot setup master outputs")
736                                               << endmsg;
737                                         break;
738                                 }
739                                 n++;
740                         }
741
742                         _master_out->allow_pan_reset ();
743                         
744                 }
745
746                 Connection* c = new OutputConnection (_("Master Out"), true);
747
748                 for (uint32_t n = 0; n < _master_out->n_inputs (); ++n) {
749                         c->add_port ();
750                         c->add_connection ((int) n, _master_out->input(n)->name());
751                 }
752                 add_connection (c);
753         } 
754
755         hookup_io ();
756
757         /* catch up on send+insert cnts */
758
759         insert_cnt = 0;
760         
761         for (slist<PortInsert*>::iterator i = _port_inserts.begin(); i != _port_inserts.end(); ++i) {
762                 uint32_t id;
763
764                 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
765                         if (id > insert_cnt) {
766                                 insert_cnt = id;
767                         }
768                 }
769         }
770
771         send_cnt = 0;
772
773         for (slist<Send*>::iterator i = _sends.begin(); i != _sends.end(); ++i) {
774                 uint32_t id;
775                 
776                 if (sscanf ((*i)->name().c_str(), "%*s %u", &id) == 1) {
777                         if (id > send_cnt) {
778                                 send_cnt = id;
779                         }
780                 }
781         }
782
783         _state_of_the_state = StateOfTheState (_state_of_the_state & ~(CannotSave|Dirty));
784
785         /* hook us up to the engine */
786
787         _engine.set_session (this);
788
789         _state_of_the_state = Clean;
790
791         DirtyChanged (); /* EMIT SIGNAL */
792 }
793
794 void
795 Session::hookup_io ()
796 {
797         /* stop graph reordering notifications from
798            causing resorts, etc.
799         */
800
801         _state_of_the_state = StateOfTheState (_state_of_the_state | InitialConnecting);
802
803         /* Tell all IO objects to create their ports */
804
805         IO::enable_ports ();
806
807         if (_control_out) {
808                 uint32_t n;
809
810                 while ((int) _control_out->n_inputs() < _control_out->input_maximum()) {
811                         if (_control_out->add_input_port ("", this)) {
812                                 error << _("cannot setup control inputs")
813                                       << endmsg;
814                                 break;
815                         }
816                 }
817                 n = 0;
818                 while ((int) _control_out->n_outputs() < _control_out->output_maximum()) {
819                         if (_control_out->add_output_port (_engine.get_nth_physical_output (n), this)) {
820                                 error << _("cannot set up master outputs")
821                                       << endmsg;
822                                 break;
823                         }
824                         n++;
825                 }
826         }
827
828         /* Tell all IO objects to connect themselves together */
829
830         IO::enable_connecting ();
831
832         /* Now reset all panners */
833
834         IO::reset_panners ();
835
836         /* Anyone who cares about input state, wake up and do something */
837
838         IOConnectionsComplete (); /* EMIT SIGNAL */
839
840         _state_of_the_state = StateOfTheState (_state_of_the_state & ~InitialConnecting);
841
842         /* now handle the whole enchilada as if it was one
843            graph reorder event.
844         */
845
846         graph_reordered ();
847
848         /* update mixer solo state */
849
850         catch_up_on_solo();
851 }
852
853 void
854 Session::playlist_length_changed (Playlist* pl)
855 {
856         /* we can't just increase end_location->end() if pl->get_maximum_extent() 
857            if larger. if the playlist used to be the longest playlist,
858            and its now shorter, we have to decrease end_location->end(). hence,
859            we have to iterate over all diskstreams and check the 
860            playlists currently in use.
861         */
862         find_current_end ();
863 }
864
865 void
866 Session::diskstream_playlist_changed (DiskStream* dstream)
867 {
868         Playlist *playlist;
869
870         if ((playlist = dstream->playlist()) != 0) {
871           playlist->LengthChanged.connect (sigc::bind (mem_fun (this, &Session::playlist_length_changed), playlist));
872         }
873         
874         /* see comment in playlist_length_changed () */
875         find_current_end ();
876 }
877
878 bool
879 Session::record_enabling_legal () const
880 {
881         /* this used to be in here, but survey says.... we don't need to restrict it */
882         // if (record_status() == Recording) {
883         //      return false;
884         // }
885
886         if (all_safe) {
887                 return false;
888         }
889         return true;
890 }
891
892 void
893 Session::set_auto_play (bool yn)
894 {
895         if (auto_play != yn) {
896                 auto_play = yn; 
897                 set_dirty ();
898                 ControlChanged (AutoPlay);
899         }
900 }
901
902 void
903 Session::set_auto_return (bool yn)
904 {
905         if (auto_return != yn) {
906                 auto_return = yn; 
907                 set_dirty ();
908                 ControlChanged (AutoReturn);
909         }
910 }
911
912 void
913 Session::set_crossfades_active (bool yn)
914 {
915         if (crossfades_active != yn) {
916                 crossfades_active = yn; 
917                 set_dirty ();
918                 ControlChanged (CrossFadesActive);
919         }
920 }
921
922 void
923 Session::set_recording_plugins (bool yn)
924 {
925         if (recording_plugins != yn) {
926                 recording_plugins = yn; 
927                 set_dirty ();
928                 ControlChanged (RecordingPlugins); 
929         }
930 }
931
932 void
933 Session::set_auto_input (bool yn)
934 {
935         if (auto_input != yn) {
936                 auto_input = yn;
937                 
938                 if (Config->get_use_hardware_monitoring() && transport_rolling()) {
939                         /* auto-input only makes a difference if we're rolling */
940
941                         /* Even though this can called from RT context we are using
942                            a non-tentative rwlock here,  because the action must occur.
943                            The rarity and short potential lock duration makes this "OK"
944                         */
945                         RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
946                         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
947                                 if ((*i)->record_enabled ()) {
948                                         //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
949                                         (*i)->monitor_input (!auto_input);   
950                                 }
951                         }
952                 }
953
954                 set_dirty();
955                 ControlChanged (AutoInput);
956         }
957 }
958
959 void
960 Session::reset_input_monitor_state ()
961 {
962         if (transport_rolling()) {
963                 RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
964                 for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
965                         if ((*i)->record_enabled ()) {
966                                 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
967                                 (*i)->monitor_input (Config->get_use_hardware_monitoring() && !auto_input);
968                         }
969                 }
970         } else {
971                 RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
972                 for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
973                         if ((*i)->record_enabled ()) {
974                                 //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl;
975                                 (*i)->monitor_input (Config->get_use_hardware_monitoring());
976                         }
977                 }
978         }
979 }
980
981
982 void
983 Session::set_input_auto_connect (bool yn)
984 {
985         if (yn) {
986                 input_auto_connect = AutoConnectOption (input_auto_connect|AutoConnectPhysical);
987         } else {
988                 input_auto_connect = AutoConnectOption (input_auto_connect|~AutoConnectPhysical);
989         }
990         set_dirty ();
991 }
992
993 bool
994 Session::get_input_auto_connect () const
995 {
996         return (input_auto_connect & AutoConnectPhysical);
997 }
998
999 void
1000 Session::set_output_auto_connect (AutoConnectOption aco)
1001 {
1002         output_auto_connect = aco;
1003         set_dirty ();
1004 }
1005
1006 void
1007 Session::auto_punch_start_changed (Location* location)
1008 {
1009         replace_event (Event::PunchIn, location->start());
1010
1011         if (get_record_enabled() && get_punch_in()) {
1012                 /* capture start has been changed, so save new pending state */
1013                 save_state ("", true);
1014         }
1015 }       
1016
1017 void
1018 Session::auto_punch_end_changed (Location* location)
1019 {
1020         jack_nframes_t when_to_stop = location->end();
1021         // when_to_stop += _worst_output_latency + _worst_input_latency;
1022         replace_event (Event::PunchOut, when_to_stop);
1023 }       
1024
1025 void
1026 Session::auto_punch_changed (Location* location)
1027 {
1028         jack_nframes_t when_to_stop = location->end();
1029
1030         replace_event (Event::PunchIn, location->start());
1031         //when_to_stop += _worst_output_latency + _worst_input_latency;
1032         replace_event (Event::PunchOut, when_to_stop);
1033 }       
1034
1035 void
1036 Session::auto_loop_changed (Location* location)
1037 {
1038         replace_event (Event::AutoLoop, location->end(), location->start());
1039
1040         if (transport_rolling() && get_auto_loop()) {
1041
1042                 //if (_transport_frame < location->start() || _transport_frame > location->end()) {
1043
1044                 if (_transport_frame > location->end()) {
1045                         // relocate to beginning of loop
1046                         clear_events (Event::LocateRoll);
1047                         
1048                         request_locate (location->start(), true);
1049
1050                 }
1051                 else if (seamless_loop && !loop_changing) {
1052                         
1053                         // schedule a locate-roll to refill the diskstreams at the
1054                         // previous loop end
1055                         loop_changing = true;
1056
1057                         if (location->end() > last_loopend) {
1058                                 clear_events (Event::LocateRoll);
1059                                 Event *ev = new Event (Event::LocateRoll, Event::Add, last_loopend, last_loopend, 0, true);
1060                                 queue_event (ev);
1061                         }
1062
1063                 }
1064         }       
1065
1066         last_loopend = location->end();
1067         
1068 }
1069
1070 void
1071 Session::set_auto_punch_location (Location* location)
1072 {
1073         Location* existing;
1074
1075         if ((existing = _locations.auto_punch_location()) != 0 && existing != location) {
1076                 auto_punch_start_changed_connection.disconnect();
1077                 auto_punch_end_changed_connection.disconnect();
1078                 auto_punch_changed_connection.disconnect();
1079                 existing->set_auto_punch (false, this);
1080                 remove_event (existing->start(), Event::PunchIn);
1081                 clear_events (Event::PunchOut);
1082                 auto_punch_location_changed (0);
1083         }
1084
1085         set_dirty();
1086
1087         if (location == 0) {
1088                 return;
1089         }
1090         
1091         if (location->end() <= location->start()) {
1092                 error << _("Session: you can't use that location for auto punch (start <= end)") << endmsg;
1093                 return;
1094         }
1095
1096         auto_punch_start_changed_connection.disconnect();
1097         auto_punch_end_changed_connection.disconnect();
1098         auto_punch_changed_connection.disconnect();
1099                 
1100         auto_punch_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_punch_start_changed));
1101         auto_punch_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_punch_end_changed));
1102         auto_punch_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_punch_changed));
1103
1104         location->set_auto_punch (true, this);
1105         auto_punch_location_changed (location);
1106 }
1107
1108 void
1109 Session::set_punch_in (bool yn)
1110 {
1111         if (punch_in == yn) {
1112                 return;
1113         }
1114
1115         Location* location;
1116
1117         if ((location = _locations.auto_punch_location()) != 0) {
1118                 if ((punch_in = yn) == true) {
1119                         replace_event (Event::PunchIn, location->start());
1120                 } else {
1121                         remove_event (location->start(), Event::PunchIn);
1122                 }
1123         }
1124
1125         set_dirty();
1126         ControlChanged (PunchIn); /* EMIT SIGNAL */
1127 }
1128
1129 void
1130 Session::set_punch_out (bool yn)
1131 {
1132         if (punch_out == yn) {
1133                 return;
1134         }
1135
1136         Location* location;
1137
1138         if ((location = _locations.auto_punch_location()) != 0) {
1139                 if ((punch_out = yn) == true) {
1140                         replace_event (Event::PunchOut, location->end());
1141                 } else {
1142                         clear_events (Event::PunchOut);
1143                 }
1144         }
1145
1146         set_dirty();
1147         ControlChanged (PunchOut); /* EMIT SIGNAL */
1148 }
1149
1150 void
1151 Session::set_auto_loop_location (Location* location)
1152 {
1153         Location* existing;
1154
1155         if ((existing = _locations.auto_loop_location()) != 0 && existing != location) {
1156                 auto_loop_start_changed_connection.disconnect();
1157                 auto_loop_end_changed_connection.disconnect();
1158                 auto_loop_changed_connection.disconnect();
1159                 existing->set_auto_loop (false, this);
1160                 remove_event (existing->end(), Event::AutoLoop);
1161                 auto_loop_location_changed (0);
1162         }
1163         
1164         set_dirty();
1165
1166         if (location == 0) {
1167                 return;
1168         }
1169
1170         if (location->end() <= location->start()) {
1171                 error << _("Session: you can't use a mark for auto loop") << endmsg;
1172                 return;
1173         }
1174
1175         last_loopend = location->end();
1176         
1177         auto_loop_start_changed_connection.disconnect();
1178         auto_loop_end_changed_connection.disconnect();
1179         auto_loop_changed_connection.disconnect();
1180         
1181         auto_loop_start_changed_connection = location->start_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1182         auto_loop_end_changed_connection = location->end_changed.connect (mem_fun (this, &Session::auto_loop_changed));
1183         auto_loop_changed_connection = location->changed.connect (mem_fun (this, &Session::auto_loop_changed));
1184
1185         location->set_auto_loop (true, this);
1186         auto_loop_location_changed (location);
1187 }
1188
1189 void
1190 Session::locations_added (Location* ignored)
1191 {
1192         set_dirty ();
1193 }
1194
1195 void
1196 Session::locations_changed ()
1197 {
1198         _locations.apply (*this, &Session::handle_locations_changed);
1199 }
1200
1201 void
1202 Session::handle_locations_changed (Locations::LocationList& locations)
1203 {
1204         Locations::LocationList::iterator i;
1205         Location* location;
1206         bool set_loop = false;
1207         bool set_punch = false;
1208
1209         for (i = locations.begin(); i != locations.end(); ++i) {
1210
1211                 location =* i;
1212
1213                 if (location->is_auto_punch()) {
1214                         set_auto_punch_location (location);
1215                         set_punch = true;
1216                 }
1217                 if (location->is_auto_loop()) {
1218                         set_auto_loop_location (location);
1219                         set_loop = true;
1220                 }
1221                 
1222         }
1223
1224         if (!set_loop) {
1225                 set_auto_loop_location (0);
1226         }
1227         if (!set_punch) {
1228                 set_auto_punch_location (0);
1229         }
1230
1231         set_dirty();
1232 }                                                    
1233
1234 void
1235 Session::enable_record ()
1236 {
1237         /* XXX really atomic compare+swap here */
1238         if (atomic_read (&_record_status) != Recording) {
1239                 atomic_set (&_record_status, Recording);
1240                 _last_record_location = _transport_frame;
1241                 send_mmc_in_another_thread (MIDI::MachineControl::cmdRecordStrobe);
1242
1243                 if (Config->get_use_hardware_monitoring() && auto_input) {
1244                         /* Even though this can be called from RT context we are using
1245                            a non-tentative rwlock here,  because the action must occur.
1246                            The rarity and short potential lock duration makes this "OK"
1247                         */
1248                         RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
1249                         
1250                         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1251                                 if ((*i)->record_enabled ()) {
1252                                         //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl;
1253                                         (*i)->monitor_input (true);   
1254                                 }
1255                         }
1256                 }
1257
1258                 RecordEnabled ();
1259         }
1260 }
1261
1262 void
1263 Session::disable_record ()
1264 {
1265         if (atomic_read (&_record_status) != Disabled) {
1266                 atomic_set (&_record_status, Disabled);
1267                 send_mmc_in_another_thread (MIDI::MachineControl::cmdRecordExit);
1268
1269                 if (Config->get_use_hardware_monitoring() && auto_input) {
1270                         /* Even though this can be called from RT context we are using
1271                            a non-tentative rwlock here,  because the action must occur.
1272                            The rarity and short potential lock duration makes this "OK"
1273                         */
1274                         RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
1275                         
1276                         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1277                                 if ((*i)->record_enabled ()) {
1278                                         //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
1279                                         (*i)->monitor_input (false);   
1280                                 }
1281                         }
1282                 }
1283                 
1284                 RecordDisabled ();
1285                 remove_pending_capture_state ();
1286
1287         }
1288 }
1289
1290 void
1291 Session::step_back_from_record ()
1292 {
1293         atomic_set (&_record_status, Enabled);
1294
1295         if (Config->get_use_hardware_monitoring()) {
1296                 /* Even though this can be called from RT context we are using
1297                    a non-tentative rwlock here,  because the action must occur.
1298                    The rarity and short potential lock duration makes this "OK"
1299                 */
1300                 RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
1301                 
1302                 for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1303                         if (auto_input && (*i)->record_enabled ()) {
1304                                 //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
1305                                 (*i)->monitor_input (false);   
1306                         }
1307                 }
1308         }
1309 }
1310
1311 void
1312 Session::maybe_enable_record ()
1313 {
1314         atomic_set (&_record_status, Enabled);
1315
1316         save_state ("", true);
1317
1318         if (_transport_speed) {
1319                 if (!punch_in) {
1320                         enable_record ();
1321                 } 
1322         } else {
1323                 send_mmc_in_another_thread (MIDI::MachineControl::cmdRecordPause);
1324                 RecordEnabled (); /* EMIT SIGNAL */
1325         }
1326
1327         set_dirty();
1328 }
1329
1330 jack_nframes_t
1331 Session::audible_frame () const
1332 {
1333         jack_nframes_t ret;
1334         jack_nframes_t offset;
1335         jack_nframes_t tf;
1336
1337         /* the first of these two possible settings for "offset"
1338            mean that the audible frame is stationary until 
1339            audio emerges from the latency compensation
1340            "pseudo-pipeline".
1341
1342            the second means that the audible frame is stationary
1343            until audio would emerge from a physical port
1344            in the absence of any plugin latency compensation
1345         */
1346
1347         offset = _worst_output_latency;
1348
1349         if (offset > current_block_size) {
1350                 offset -= current_block_size;
1351         } else { 
1352                 /* XXX is this correct? if we have no external
1353                    physical connections and everything is internal
1354                    then surely this is zero? still, how
1355                    likely is that anyway?
1356                 */
1357                 offset = current_block_size;
1358         }
1359
1360         if (synced_to_jack()) {
1361                 tf = _engine.transport_frame();
1362         } else {
1363                 tf = _transport_frame;
1364         }
1365
1366         if (_transport_speed == 0) {
1367                 return tf;
1368         }
1369
1370         if (tf < offset) {
1371                 return 0;
1372         }
1373
1374         ret = tf;
1375
1376         if (!non_realtime_work_pending()) {
1377
1378                 /* MOVING */
1379
1380                 /* take latency into account */
1381                 
1382                 ret -= offset;
1383         }
1384
1385         return ret;
1386 }
1387
1388 void
1389 Session::set_frame_rate (jack_nframes_t frames_per_second)
1390 {
1391         /** \fn void Session::set_frame_size(jack_nframes_t)
1392                 the AudioEngine object that calls this guarantees 
1393                 that it will not be called while we are also in
1394                 ::process(). Its fine to do things that block
1395                 here.
1396         */
1397
1398         _current_frame_rate = frames_per_second;
1399         _frames_per_smpte_frame = (double) _current_frame_rate / (double) smpte_frames_per_second;
1400
1401         Route::set_automation_interval ((jack_nframes_t) ceil ((double) frames_per_second * 0.25));
1402
1403         set_dirty();
1404
1405         /* XXX need to reset/reinstantiate all LADSPA plugins */
1406 }
1407
1408 void
1409 Session::set_block_size (jack_nframes_t nframes)
1410 {
1411         /* the AudioEngine guarantees 
1412            that it will not be called while we are also in
1413            ::process(). It is therefore fine to do things that block
1414            here.
1415         */
1416
1417         { 
1418                 RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
1419                 RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__);
1420                 vector<Sample*>::iterator i;
1421                 uint32_t np;
1422                         
1423                 current_block_size = nframes;
1424                 
1425                 for (np = 0, i = _passthru_buffers.begin(); i != _passthru_buffers.end(); ++i, ++np) {
1426                         free (*i);
1427                 }
1428
1429                 for (vector<Sample*>::iterator i = _silent_buffers.begin(); i != _silent_buffers.end(); ++i) {
1430                         free (*i);
1431                 }
1432
1433                 _passthru_buffers.clear ();
1434                 _silent_buffers.clear ();
1435
1436                 ensure_passthru_buffers (np);
1437
1438                 if (_gain_automation_buffer) {
1439                         delete [] _gain_automation_buffer;
1440                 }
1441                 _gain_automation_buffer = new gain_t[nframes];
1442
1443                 allocate_pan_automation_buffers (nframes, _npan_buffers, true);
1444
1445                 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
1446                         (*i)->set_block_size (nframes);
1447                 }
1448                 
1449                 for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
1450                         (*i)->set_block_size (nframes);
1451                 }
1452
1453                 set_worst_io_latencies (false);
1454         }
1455 }
1456
1457 void
1458 Session::set_default_fade (float steepness, float fade_msecs)
1459 {
1460 #if 0
1461         jack_nframes_t fade_frames;
1462         
1463         /* Don't allow fade of less 1 frame */
1464         
1465         if (fade_msecs < (1000.0 * (1.0/_current_frame_rate))) {
1466
1467                 fade_msecs = 0;
1468                 fade_frames = 0;
1469
1470         } else {
1471                 
1472                 fade_frames = (jack_nframes_t) floor (fade_msecs * _current_frame_rate * 0.001);
1473                 
1474         }
1475
1476         default_fade_msecs = fade_msecs;
1477         default_fade_steepness = steepness;
1478
1479         {
1480                 // jlc, WTF is this!
1481                 RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
1482                 AudioRegion::set_default_fade (steepness, fade_frames);
1483         }
1484
1485         set_dirty();
1486
1487         /* XXX have to do this at some point */
1488         /* foreach region using default fade, reset, then 
1489            refill_all_diskstream_buffers ();
1490         */
1491 #endif
1492 }
1493
1494 struct RouteSorter {
1495     bool operator() (Route* r1, Route* r2) {
1496             if (r1->fed_by.find (r2) != r1->fed_by.end()) {
1497                     return false;
1498             } else if (r2->fed_by.find (r1) != r2->fed_by.end()) {
1499                     return true;
1500             } else {
1501                     if (r1->fed_by.empty()) {
1502                             if (r2->fed_by.empty()) {
1503                                     /* no ardour-based connections inbound to either route. just use signal order */
1504                                     return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1505                             } else {
1506                                     /* r2 has connections, r1 does not; run r1 early */
1507                                     return true;
1508                             }
1509                     } else {
1510                             return r1->order_key(N_("signal")) < r2->order_key(N_("signal"));
1511                     }
1512             }
1513     }
1514 };
1515
1516 static void
1517 trace_terminal (Route* r1, Route* rbase)
1518 {
1519         Route* r2;
1520
1521         if ((r1->fed_by.find (rbase) != r1->fed_by.end()) && (rbase->fed_by.find (r1) != rbase->fed_by.end())) {
1522                 info << string_compose(_("feedback loop setup between %1 and %2"), r1->name(), rbase->name()) << endmsg;
1523                 return;
1524         } 
1525
1526         /* make a copy of the existing list of routes that feed r1 */
1527
1528         set<Route *> existing = r1->fed_by;
1529
1530         /* for each route that feeds r1, recurse, marking it as feeding
1531            rbase as well.
1532         */
1533
1534         for (set<Route *>::iterator i = existing.begin(); i != existing.end(); ++i) {
1535                 r2 =* i;
1536
1537                 /* r2 is a route that feeds r1 which somehow feeds base. mark
1538                    base as being fed by r2
1539                 */
1540
1541                 rbase->fed_by.insert (r2);
1542
1543                 if (r2 != rbase) {
1544
1545                         /* 2nd level feedback loop detection. if r1 feeds or is fed by r2,
1546                            stop here.
1547                          */
1548
1549                         if ((r1->fed_by.find (r2) != r1->fed_by.end()) && (r2->fed_by.find (r1) != r2->fed_by.end())) {
1550                                 continue;
1551                         }
1552
1553                         /* now recurse, so that we can mark base as being fed by
1554                            all routes that feed r2
1555                         */
1556
1557                         trace_terminal (r2, rbase);
1558                 }
1559
1560         }
1561 }
1562
1563 void
1564 Session::resort_routes (void* src)
1565 {
1566         /* don't do anything here with signals emitted
1567            by Routes while we are being destroyed.
1568         */
1569
1570         if (_state_of_the_state & Deletion) {
1571                 return;
1572         }
1573
1574         /* Caller MUST hold the route_lock */
1575
1576         RouteList::iterator i, j;
1577
1578         for (i = routes.begin(); i != routes.end(); ++i) {
1579
1580                 (*i)->fed_by.clear ();
1581                 
1582                 for (j = routes.begin(); j != routes.end(); ++j) {
1583
1584                         /* although routes can feed themselves, it will
1585                            cause an endless recursive descent if we
1586                            detect it. so don't bother checking for
1587                            self-feeding.
1588                         */
1589
1590                         if (*j == *i) {
1591                                 continue;
1592                         }
1593
1594                         if ((*j)->feeds (*i)) {
1595                                 (*i)->fed_by.insert (*j);
1596                         } 
1597                 }
1598         }
1599         
1600         for (i = routes.begin(); i != routes.end(); ++i) {
1601                 trace_terminal (*i, *i);
1602         }
1603
1604         RouteSorter cmp;
1605         routes.sort (cmp);
1606
1607 #if 0
1608         cerr << "finished route resort\n";
1609         
1610         for (i = routes.begin(); i != routes.end(); ++i) {
1611                 cerr << " " << (*i)->name() << " signal order = " << (*i)->order_key ("signal") << endl;
1612         }
1613         cerr << endl;
1614 #endif
1615
1616 }
1617
1618 AudioTrack*
1619 Session::new_audio_track (int input_channels, int output_channels)
1620 {
1621         AudioTrack *track;
1622         char track_name[32];
1623         uint32_t n = 0;
1624         uint32_t channels_used = 0;
1625         string port;
1626         uint32_t nphysical_in;
1627         uint32_t nphysical_out;
1628
1629         /* count existing audio tracks */
1630
1631         {
1632                 RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
1633                 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
1634                         if (dynamic_cast<AudioTrack*>(*i) != 0) {
1635                                 if (!(*i)->hidden()) {
1636                                         n++;
1637                                         channels_used += (*i)->n_inputs();
1638                                 }
1639                         }
1640                 }
1641         }
1642
1643         /* check for duplicate route names, since we might have pre-existing
1644            routes with this name (e.g. create Audio1, Audio2, delete Audio1,
1645            save, close,restart,add new route - first named route is now
1646            Audio2)
1647         */
1648
1649         do {
1650                 snprintf (track_name, sizeof(track_name), "Audio %" PRIu32, n+1);
1651                 if (route_by_name (track_name) == 0) {
1652                         break;
1653                 }
1654                 n++;
1655
1656         } while (n < (UINT_MAX-1));
1657
1658         if (input_auto_connect & AutoConnectPhysical) {
1659                 nphysical_in = n_physical_inputs;
1660         } else {
1661                 nphysical_in = 0;
1662         }
1663
1664         if (output_auto_connect & AutoConnectPhysical) {
1665                 nphysical_out = n_physical_outputs;
1666         } else {
1667                 nphysical_out = 0;
1668         }
1669
1670         try {
1671                 track = new AudioTrack (*this, track_name);
1672
1673                 if (track->ensure_io (input_channels, output_channels, false, this)) {
1674                         error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1675                                           input_channels, output_channels)
1676                               << endmsg;
1677                 }
1678
1679                 if (nphysical_in) {
1680                         for (uint32_t x = 0; x < track->n_inputs() && x < nphysical_in; ++x) {
1681                                 
1682                                 port = "";
1683                                 
1684                                 if (input_auto_connect & AutoConnectPhysical) {
1685                                         port = _engine.get_nth_physical_input ((channels_used+x)%nphysical_in);
1686                                 } 
1687                                 
1688                                 if (port.length() && track->connect_input (track->input (x), port, this)) {
1689                                         break;
1690                                 }
1691                         }
1692                 }
1693                 
1694                 for (uint32_t x = 0; x < track->n_outputs(); ++x) {
1695                         
1696                         port = "";
1697
1698                         if (nphysical_out && (output_auto_connect & AutoConnectPhysical)) {
1699                                 port = _engine.get_nth_physical_output ((channels_used+x)%nphysical_out);
1700                         } else if (output_auto_connect & AutoConnectMaster) {
1701                                 if (_master_out) {
1702                                         port = _master_out->input (x%_master_out->n_inputs())->name();
1703                                 }
1704                         }
1705
1706                         if (port.length() && track->connect_output (track->output (x), port, this)) {
1707                                 break;
1708                         }
1709                 }
1710
1711                 if (_control_out) {
1712                         vector<string> cports;
1713                         uint32_t ni = _control_out->n_inputs();
1714
1715                         for (n = 0; n < ni; ++n) {
1716                                 cports.push_back (_control_out->input(n)->name());
1717                         }
1718
1719                         track->set_control_outs (cports);
1720                 }
1721
1722                 track->diskstream_changed.connect (mem_fun (this, &Session::resort_routes));
1723
1724                 add_route (track);
1725
1726                 track->set_remote_control_id (ntracks());
1727         }
1728
1729         catch (failed_constructor &err) {
1730                 error << _("Session: could not create new audio track.") << endmsg;
1731                 return 0;
1732         }
1733
1734         return track;
1735 }
1736
1737 Route*
1738 Session::new_audio_route (int input_channels, int output_channels)
1739 {
1740         Route *bus;
1741         char bus_name[32];
1742         uint32_t n = 0;
1743         string port;
1744
1745         /* count existing audio busses */
1746
1747         {
1748                 RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
1749                 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
1750                         if (dynamic_cast<AudioTrack*>(*i) == 0) {
1751                                 if (!(*i)->hidden()) {
1752                                         n++;
1753                                 }
1754                         }
1755                 }
1756         }
1757
1758         do {
1759                 snprintf (bus_name, sizeof(bus_name), "Bus %" PRIu32, n+1);
1760                 if (route_by_name (bus_name) == 0) {
1761                         break;
1762                 }
1763                 n++;
1764
1765         } while (n < (UINT_MAX-1));
1766
1767         try {
1768                 bus = new Route (*this, bus_name, -1, -1, -1, -1);
1769
1770                 if (bus->ensure_io (input_channels, output_channels, false, this)) {
1771                         error << string_compose (_("cannot configure %1 in/%2 out configuration for new audio track"),
1772                                           input_channels, output_channels)
1773                               << endmsg;
1774                 }
1775
1776                 for (uint32_t x = 0; x < bus->n_inputs(); ++x) {
1777                         
1778                         port = "";
1779
1780                         if (input_auto_connect & AutoConnectPhysical) {
1781                                 port = _engine.get_nth_physical_input ((n+x)%n_physical_inputs);
1782                         } 
1783                         
1784                         if (port.length() && bus->connect_input (bus->input (x), port, this)) {
1785                                 break;
1786                         }
1787                 }
1788
1789                 for (uint32_t x = 0; x < bus->n_outputs(); ++x) {
1790                         
1791                         port = "";
1792
1793                         if (output_auto_connect & AutoConnectPhysical) {
1794                                 port = _engine.get_nth_physical_input ((n+x)%n_physical_outputs);
1795                         } else if (output_auto_connect & AutoConnectMaster) {
1796                                 if (_master_out) {
1797                                         port = _master_out->input (x%_master_out->n_inputs())->name();
1798                                 }
1799                         }
1800
1801                         if (port.length() && bus->connect_output (bus->output (x), port, this)) {
1802                                 break;
1803                         }
1804                 }
1805
1806                 if (_control_out) {
1807                         vector<string> cports;
1808                         uint32_t ni = _control_out->n_inputs();
1809
1810                         for (uint32_t n = 0; n < ni; ++n) {
1811                                 cports.push_back (_control_out->input(n)->name());
1812                         }
1813                         bus->set_control_outs (cports);
1814                 }
1815                 
1816                 add_route (bus);
1817         }
1818
1819         catch (failed_constructor &err) {
1820                 error << _("Session: could not create new route.") << endmsg;
1821                 return 0;
1822         }
1823
1824         return bus;
1825 }
1826
1827 void
1828 Session::add_route (Route* route)
1829 {
1830         { 
1831                 RWLockMonitor lm (route_lock, true, __LINE__, __FILE__);
1832                 routes.push_front (route);
1833                 resort_routes(0);
1834         }
1835
1836         route->solo_changed.connect (sigc::bind (mem_fun (*this, &Session::route_solo_changed), route));
1837         route->mute_changed.connect (mem_fun (*this, &Session::route_mute_changed));
1838         route->output_changed.connect (mem_fun (*this, &Session::set_worst_io_latencies_x));
1839         route->redirects_changed.connect (mem_fun (*this, &Session::update_latency_compensation_proxy));
1840
1841         if (route->master()) {
1842                 _master_out = route;
1843         }
1844
1845         if (route->control()) {
1846                 _control_out = route;
1847         }
1848
1849         set_dirty();
1850         save_state (_current_snapshot_name);
1851
1852         RouteAdded (route); /* EMIT SIGNAL */
1853 }
1854
1855 void
1856 Session::add_diskstream (DiskStream* dstream)
1857 {
1858         /* need to do this in case we're rolling at the time, to prevent false underruns */
1859         dstream->do_refill(0, 0);
1860         
1861         { 
1862                 RWLockMonitor lm (diskstream_lock, true, __LINE__, __FILE__);
1863                 diskstreams.push_back (dstream);
1864         }
1865
1866         /* take a reference to the diskstream, preventing it from
1867            ever being deleted until the session itself goes away,
1868            or chooses to remove it for its own purposes.
1869         */
1870
1871         dstream->ref();
1872         dstream->set_block_size (current_block_size);
1873
1874         dstream->PlaylistChanged.connect (sigc::bind (mem_fun (*this, &Session::diskstream_playlist_changed), dstream));
1875         /* this will connect to future changes, and check the current length */
1876         diskstream_playlist_changed (dstream);
1877
1878         dstream->prepare ();
1879
1880         set_dirty();
1881         save_state (_current_snapshot_name);
1882
1883         DiskStreamAdded (dstream); /* EMIT SIGNAL */
1884 }
1885
1886 void
1887 Session::remove_route (Route& route)
1888 {
1889         {       
1890                 RWLockMonitor lm (route_lock, true, __LINE__, __FILE__);
1891                 routes.remove (&route);
1892                 
1893                 /* deleting the master out seems like a dumb
1894                    idea, but its more of a UI policy issue
1895                    than our concern.
1896                 */
1897
1898                 if (&route == _master_out) {
1899                         _master_out = 0;
1900                 }
1901
1902                 if (&route == _control_out) {
1903                         _control_out = 0;
1904
1905                         /* cancel control outs for all routes */
1906
1907                         vector<string> empty;
1908
1909                         for (RouteList::iterator r = routes.begin(); r != routes.end(); ++r) {
1910                                 (*r)->set_control_outs (empty);
1911                         }
1912                 }
1913
1914                 update_route_solo_state ();
1915         }
1916
1917         {
1918                 RWLockMonitor lm (diskstream_lock, true, __LINE__, __FILE__);
1919
1920                 AudioTrack* at;
1921
1922                 if ((at = dynamic_cast<AudioTrack*>(&route)) != 0) {
1923                         diskstreams.remove (&at->disk_stream());
1924                         at->disk_stream().unref ();
1925                 }
1926
1927                 find_current_end ();
1928         }
1929         
1930         update_latency_compensation (false, false);
1931         set_dirty();
1932         
1933         /* XXX should we disconnect from the Route's signals ? */
1934
1935         save_state (_current_snapshot_name);
1936
1937         delete &route;
1938 }       
1939
1940 void
1941 Session::route_mute_changed (void* src)
1942 {
1943         set_dirty ();
1944 }
1945
1946 void
1947 Session::route_solo_changed (void* src, Route* route)
1948 {      
1949         if (solo_update_disabled) {
1950                 // We know already
1951                 return;
1952         }
1953         
1954         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
1955         bool is_track;
1956         
1957         is_track = (dynamic_cast<AudioTrack*>(route) != 0);
1958         
1959         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
1960                 
1961                 /* soloing a track mutes all other tracks, soloing a bus mutes all other busses */
1962                 
1963                 if (is_track) {
1964                         
1965                         /* don't mess with busses */
1966                         
1967                         if (dynamic_cast<AudioTrack*>(*i) == 0) {
1968                                 continue;
1969                         }
1970                         
1971                 } else {
1972                         
1973                         /* don't mess with tracks */
1974                         
1975                         if (dynamic_cast<AudioTrack*>(*i) != 0) {
1976                                 continue;
1977                         }
1978                 }
1979                 
1980                 if ((*i) != route &&
1981                     ((*i)->mix_group () == 0 ||
1982                      (*i)->mix_group () != route->mix_group () ||
1983                      !route->mix_group ()->is_active())) {
1984                         
1985                         if ((*i)->soloed()) {
1986                                 
1987                                 /* if its already soloed, and solo latching is enabled,
1988                                    then leave it as it is.
1989                                 */
1990                                 
1991                                 if (_solo_latched) {
1992                                         continue;
1993                                 } 
1994                         }
1995                         
1996                         /* do it */
1997
1998                         solo_update_disabled = true;
1999                         (*i)->set_solo (false, src);
2000                         solo_update_disabled = false;
2001                 }
2002         }
2003         
2004         bool something_soloed = false;
2005         bool same_thing_soloed = false;
2006         bool signal = false;
2007
2008         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2009                 if ((*i)->soloed()) {
2010                         something_soloed = true;
2011                         if (dynamic_cast<AudioTrack*>(*i)) {
2012                                 if (is_track) {
2013                                         same_thing_soloed = true;
2014                                         break;
2015                                 }
2016                         } else {
2017                                 if (!is_track) {
2018                                         same_thing_soloed = true;
2019                                         break;
2020                                 }
2021                         }
2022                         break;
2023                 }
2024         }
2025         
2026         if (something_soloed != currently_soloing) {
2027                 signal = true;
2028                 currently_soloing = something_soloed;
2029         }
2030         
2031         modify_solo_mute (is_track, same_thing_soloed);
2032
2033         if (signal) {
2034                 SoloActive (currently_soloing);
2035         }
2036
2037         set_dirty();
2038 }
2039
2040 void
2041 Session::set_solo_latched (bool yn)
2042 {
2043         if (yn != _solo_latched) {
2044                 _solo_latched = yn;
2045                 set_dirty ();
2046                 ControlChanged (SoloLatch);
2047         }
2048 }
2049
2050 void
2051 Session::update_route_solo_state ()
2052 {
2053         bool mute = false;
2054         bool is_track = false;
2055         bool signal = false;
2056
2057         /* caller must hold RouteLock */
2058
2059         /* this is where we actually implement solo by changing
2060            the solo mute setting of each track.
2061         */
2062                 
2063         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2064                 if ((*i)->soloed()) {
2065                         mute = true;
2066                         if (dynamic_cast<AudioTrack*>(*i)) {
2067                                 is_track = true;
2068                         }
2069                         break;
2070                 }
2071         }
2072
2073         if (mute != currently_soloing) {
2074                 signal = true;
2075                 currently_soloing = mute;
2076         }
2077
2078         if (!is_track && !mute) {
2079
2080                 /* nothing is soloed */
2081
2082                 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2083                         (*i)->set_solo_mute (false);
2084                 }
2085                 
2086                 if (signal) {
2087                         SoloActive (false);
2088                 }
2089
2090                 return;
2091         }
2092
2093         modify_solo_mute (is_track, mute);
2094
2095         if (signal) {
2096                 SoloActive (currently_soloing);
2097         }
2098 }
2099
2100 void
2101 Session::modify_solo_mute (bool is_track, bool mute)
2102 {
2103         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2104                 
2105                 if (is_track) {
2106                         
2107                         /* only alter track solo mute */
2108                         
2109                         if (dynamic_cast<AudioTrack*>(*i)) {
2110                                 if ((*i)->soloed()) {
2111                                         (*i)->set_solo_mute (!mute);
2112                                 } else {
2113                                         (*i)->set_solo_mute (mute);
2114                                 }
2115                         }
2116
2117                 } else {
2118
2119                         /* only alter bus solo mute */
2120
2121                         if (!dynamic_cast<AudioTrack*>(*i)) {
2122
2123                                 if ((*i)->soloed()) {
2124
2125                                         (*i)->set_solo_mute (false);
2126
2127                                 } else {
2128
2129                                         /* don't mute master or control outs
2130                                            in response to another bus solo
2131                                         */
2132                                         
2133                                         if ((*i) != _master_out &&
2134                                             (*i) != _control_out) {
2135                                                 (*i)->set_solo_mute (mute);
2136                                         }
2137                                 }
2138                         }
2139
2140                 }
2141         }
2142 }       
2143
2144
2145 void
2146 Session::catch_up_on_solo ()
2147 {
2148         /* this is called after set_state() to catch the full solo
2149            state, which can't be correctly determined on a per-route
2150            basis, but needs the global overview that only the session
2151            has.
2152         */
2153         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
2154         update_route_solo_state();
2155 }       
2156                 
2157 Route *
2158 Session::route_by_name (string name)
2159 {
2160         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
2161
2162         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2163                 if ((*i)->name() == name) {
2164                         return* i;
2165                 }
2166         }
2167
2168         return 0;
2169 }
2170
2171 void
2172 Session::find_current_end ()
2173 {
2174         jack_nframes_t max = 0;
2175         jack_nframes_t me; 
2176
2177         if (_state_of_the_state & Loading) {
2178                 return;
2179         }
2180
2181         /* Don't take the diskstream lock. Caller must have other ways to
2182            ensure atomicity.
2183         */
2184
2185         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2186                 Playlist* pl = (*i)->playlist();
2187                 if ((me = pl->get_maximum_extent()) > max) {
2188                         max = me;
2189                 }
2190         }
2191         
2192         if (max > end_location->end()) {
2193                 end_location->set_end (max);
2194                 set_dirty();
2195                 DurationChanged(); /* EMIT SIGNAL */
2196         }
2197 }
2198
2199 DiskStream *
2200 Session::diskstream_by_name (string name)
2201 {
2202         RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__);
2203
2204         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2205                 if ((*i)->name() == name) {
2206                         return* i;
2207                 }
2208         }
2209
2210         return 0;
2211 }
2212
2213 DiskStream *
2214 Session::diskstream_by_id (id_t id)
2215 {
2216         RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__);
2217
2218         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2219                 if ((*i)->id() == id) {
2220                         return *i;
2221                 }
2222         }
2223
2224         return 0;
2225 }
2226
2227 /* AudioRegion management */
2228
2229 string
2230 Session::new_region_name (string old)
2231 {
2232         string::size_type last_period;
2233         uint32_t number;
2234         string::size_type len = old.length() + 64;
2235         char buf[len];
2236
2237         if ((last_period = old.find_last_of ('.')) == string::npos) {
2238                 
2239                 /* no period present - add one explicitly */
2240
2241                 old += '.';
2242                 last_period = old.length() - 1;
2243                 number = 0;
2244
2245         } else {
2246
2247                 number = atoi (old.substr (last_period+1).c_str());
2248
2249         }
2250
2251         while (number < (UINT_MAX-1)) {
2252
2253                 AudioRegionList::const_iterator i;
2254                 string sbuf;
2255
2256                 number++;
2257
2258                 snprintf (buf, len, "%s%" PRIu32, old.substr (0, last_period + 1).c_str(), number);
2259                 sbuf = buf;
2260
2261                 for (i = audio_regions.begin(); i != audio_regions.end(); ++i) {
2262                         if ((*i).second->name() == sbuf) {
2263                                 break;
2264                         }
2265                 }
2266                 
2267                 if (i == audio_regions.end()) {
2268                         break;
2269                 }
2270         }
2271
2272         if (number != (UINT_MAX-1)) {
2273                 return buf;
2274         } 
2275
2276         error << string_compose (_("cannot create new name for region \"%1\""), old) << endmsg;
2277         return old;
2278 }
2279
2280 int
2281 Session::region_name (string& result, string base, bool newlevel) const
2282 {
2283         char buf[16];
2284         string subbase;
2285
2286         if (base == "") {
2287                 
2288                 LockMonitor lm (region_lock, __LINE__, __FILE__);
2289
2290                 snprintf (buf, sizeof (buf), "%d", (int)audio_regions.size() + 1);
2291
2292                 
2293                 result = "region.";
2294                 result += buf;
2295
2296         } else {
2297
2298                 /* XXX this is going to be slow. optimize me later */
2299                 
2300                 if (newlevel) {
2301                         subbase = base;
2302                 } else {
2303                         string::size_type pos;
2304
2305                         if ((pos = base.find_last_of ('-')) == string::npos) {
2306                                 pos = base.find_last_of ('.');
2307                         }
2308
2309                         /* pos may be npos, but then we just use entire base */
2310
2311                         subbase = base.substr (0, pos);
2312                 }
2313                 
2314                 bool name_taken = true;
2315                 
2316                 {
2317                         LockMonitor lm (region_lock, __LINE__, __FILE__);
2318                         
2319                         for (int n = 1; n < 5000; ++n) {
2320                                 
2321                                 result = subbase;
2322                                 snprintf (buf, sizeof (buf), ".%d", n);
2323                                 result += buf;
2324                                 
2325                                 name_taken = false;
2326                                 
2327                                 for (AudioRegionList::const_iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) {
2328                                         if ((*i).second->name() == result) {
2329                                                 name_taken = true;
2330                                                 break;
2331                                         }
2332                                 }
2333                                 
2334                                 if (!name_taken) {
2335                                         break;
2336                                 }
2337                         }
2338                 }
2339                         
2340                 if (name_taken) {
2341                         fatal << string_compose(_("too many regions with names like %1"), base) << endmsg;
2342                         /*NOTREACHED*/
2343                 }
2344         }
2345
2346         return 0;
2347 }       
2348
2349 void
2350 Session::add_region (Region* region)
2351 {
2352         AudioRegion* ar = 0;
2353         AudioRegion* oar = 0;
2354         bool added = false;
2355
2356         { 
2357                 LockMonitor lm (region_lock, __LINE__, __FILE__);
2358
2359                 if ((ar = dynamic_cast<AudioRegion*> (region)) != 0) {
2360
2361                         AudioRegionList::iterator x;
2362
2363                         for (x = audio_regions.begin(); x != audio_regions.end(); ++x) {
2364
2365                                 oar = dynamic_cast<AudioRegion*> (x->second);
2366
2367                                 if (ar->region_list_equivalent (*oar)) {
2368                                         break;
2369                                 }
2370                         }
2371
2372                         if (x == audio_regions.end()) {
2373
2374                                 pair<AudioRegionList::key_type, AudioRegionList::mapped_type> entry;
2375         
2376                                 entry.first = region->id();
2377                                 entry.second = ar;
2378
2379                                 pair<AudioRegionList::iterator,bool> x = audio_regions.insert (entry);
2380                                 
2381                                 if (!x.second) {
2382                                         return;
2383                                 }
2384
2385                                 added = true;
2386                         } 
2387
2388                 } else {
2389
2390                         fatal << _("programming error: ")
2391                               << X_("unknown region type passed to Session::add_region()")
2392                               << endmsg;
2393                         /*NOTREACHED*/
2394
2395                 }
2396         }
2397
2398         /* mark dirty because something has changed even if we didn't
2399            add the region to the region list.
2400         */
2401         
2402         set_dirty();
2403         
2404         if (added) {
2405                 region->GoingAway.connect (mem_fun (*this, &Session::remove_region));
2406                 region->StateChanged.connect (sigc::bind (mem_fun (*this, &Session::region_changed), region));
2407                 AudioRegionAdded (ar); /* EMIT SIGNAL */
2408         }
2409 }
2410
2411 void
2412 Session::region_changed (Change what_changed, Region* region)
2413 {
2414         if (what_changed & Region::HiddenChanged) {
2415                 /* relay hidden changes */
2416                 RegionHiddenChange (region);
2417         }
2418 }
2419
2420 void
2421 Session::region_renamed (Region* region)
2422 {
2423         add_region (region);
2424 }
2425
2426 void
2427 Session::remove_region (Region* region)
2428 {
2429         AudioRegionList::iterator i;
2430         AudioRegion* ar = 0;
2431         bool removed = false;
2432
2433         { 
2434                 LockMonitor lm (region_lock, __LINE__, __FILE__);
2435
2436                 if ((ar = dynamic_cast<AudioRegion*> (region)) != 0) {
2437                         if ((i = audio_regions.find (region->id())) != audio_regions.end()) {
2438                                 audio_regions.erase (i);
2439                                 removed = true;
2440                         } 
2441                 } else {
2442                         fatal << _("programming error: ") 
2443                               << X_("unknown region type passed to Session::remove_region()")
2444                               << endmsg;
2445                         /*NOTREACHED*/
2446                 }
2447         }
2448
2449         /* mark dirty because something has changed even if we didn't
2450            remove the region from the region list.
2451         */
2452
2453         set_dirty();
2454
2455         if (removed) {
2456                  AudioRegionRemoved(ar); /* EMIT SIGNAL */
2457         }
2458 }
2459
2460 AudioRegion*
2461 Session::find_whole_file_parent (AudioRegion& child)
2462 {
2463         AudioRegionList::iterator i;
2464         AudioRegion* region;
2465         LockMonitor lm (region_lock, __LINE__, __FILE__);
2466
2467         for (i = audio_regions.begin(); i != audio_regions.end(); ++i) {
2468
2469                 region = (*i).second;
2470
2471                 if (region->whole_file()) {
2472
2473                         if (child.source_equivalent (*region)) {
2474                                 return region;
2475                         }
2476                 }
2477         } 
2478
2479         return 0;
2480 }       
2481
2482 void
2483 Session::find_equivalent_playlist_regions (AudioRegion& region, vector<AudioRegion*>& result)
2484 {
2485         for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
2486
2487                 AudioPlaylist* pl;
2488
2489                 if ((pl = dynamic_cast<AudioPlaylist*>(*i)) == 0) {
2490                         continue;
2491                 }
2492
2493                 pl->get_region_list_equivalent_regions (region, result);
2494         }
2495 }
2496
2497 int
2498 Session::destroy_region (Region* region)
2499 {
2500         AudioRegion* aregion;
2501
2502         if ((aregion = dynamic_cast<AudioRegion*> (region)) == 0) {
2503                 return 0;
2504         }
2505
2506         if (aregion->playlist()) {
2507                 aregion->playlist()->destroy_region (region);
2508         }
2509
2510         vector<Source*> srcs;
2511         
2512         for (uint32_t n = 0; n < aregion->n_channels(); ++n) {
2513                 srcs.push_back (&aregion->source (n));
2514         }
2515
2516         for (vector<Source*>::iterator i = srcs.begin(); i != srcs.end(); ++i) {
2517                 
2518                 if ((*i)->use_cnt() == 0) {
2519                         (*i)->mark_for_remove ();
2520                         delete *i;
2521                 }
2522         }
2523
2524         return 0;
2525 }
2526
2527 int
2528 Session::destroy_regions (list<Region*> regions)
2529 {
2530         for (list<Region*>::iterator i = regions.begin(); i != regions.end(); ++i) {
2531                 destroy_region (*i);
2532         }
2533         return 0;
2534 }
2535
2536 int
2537 Session::remove_last_capture ()
2538 {
2539         list<Region*> r;
2540
2541         RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__);
2542         
2543         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2544                 list<Region*>& l = (*i)->last_capture_regions();
2545                 
2546                 if (!l.empty()) {
2547                         r.insert (r.end(), l.begin(), l.end());
2548                         l.clear ();
2549                 }
2550         }
2551
2552         destroy_regions (r);
2553         return 0;
2554 }
2555
2556 int
2557 Session::remove_region_from_region_list (Region& r)
2558 {
2559         remove_region (&r);
2560         return 0;
2561 }
2562
2563 /* Source Management */
2564
2565 void
2566 Session::add_source (Source* source)
2567 {
2568         pair<SourceList::key_type, SourceList::mapped_type> entry;
2569         
2570         {
2571                 LockMonitor lm (source_lock, __LINE__, __FILE__);
2572                 entry.first = source->id();
2573                 entry.second = source;
2574                 sources.insert (entry);
2575         }
2576         
2577         source->GoingAway.connect (mem_fun (this, &Session::remove_source));
2578         set_dirty();
2579         
2580         SourceAdded (source); /* EMIT SIGNAL */
2581 }
2582
2583 void
2584 Session::remove_source (Source* source)
2585 {
2586         SourceList::iterator i;
2587
2588         { 
2589                 LockMonitor lm (source_lock, __LINE__, __FILE__);
2590
2591                 if ((i = sources.find (source->id())) != sources.end()) {
2592                         sources.erase (i);
2593                 }
2594         }
2595
2596         if (!_state_of_the_state & InCleanup) {
2597
2598                 /* save state so we don't end up with a session file
2599                    referring to non-existent sources.
2600                 */
2601                 
2602                 save_state (_current_snapshot_name);
2603         }
2604
2605         SourceRemoved(source); /* EMIT SIGNAL */
2606 }
2607
2608 Source *
2609 Session::get_source (ARDOUR::id_t id)
2610 {
2611         LockMonitor lm (source_lock, __LINE__, __FILE__);
2612         SourceList::iterator i;
2613         Source* source = 0;
2614
2615         if ((i = sources.find (id)) != sources.end()) {
2616                 source = (*i).second;
2617         }
2618
2619         return source;
2620 }
2621
2622 FileSource *
2623 Session::create_file_source (DiskStream& ds, int32_t chan, bool destructive)
2624 {
2625         string spath;
2626         uint32_t cnt;
2627         char buf[PATH_MAX+1];
2628         const uint32_t limit = 10000;
2629         string legalized;
2630
2631         buf[0] = '\0';
2632         legalized = legalize_for_path (ds.name());
2633
2634         /* find a "version" of the file name that doesn't exist in
2635            any of the possible directories.
2636         */
2637         
2638         for (cnt = 1; cnt <= limit; ++cnt) {
2639
2640                 vector<space_and_path>::iterator i;
2641                 uint32_t existing = 0;
2642
2643                 for (i = session_dirs.begin(); i != session_dirs.end(); ++i) {
2644
2645                         spath = (*i).path;
2646                         spath += sound_dir_name;
2647                         spath += '/';
2648                         spath += legalized;
2649
2650                         if (ds.n_channels() < 2) {
2651                                 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
2652                         } else if (ds.n_channels() == 2) {
2653                                 if (chan == 0) {
2654                                         snprintf (buf, sizeof(buf), "%s-%u%%L.wav", spath.c_str(), cnt);
2655                                 } else {
2656                                         snprintf (buf, sizeof(buf), "%s-%u%%R.wav", spath.c_str(), cnt);
2657                                 }
2658                         } else if (ds.n_channels() < 26) {
2659                                 snprintf (buf, sizeof(buf), "%s-%u%%%c.wav", spath.c_str(), cnt, 'a' + chan);
2660                         } else {
2661                                 snprintf (buf, sizeof(buf), "%s-%u.wav", spath.c_str(), cnt);
2662                         }
2663
2664                         if (access (buf, F_OK) == 0) {
2665                                 existing++;
2666                         }
2667                 }
2668
2669                 if (existing == 0) {
2670                         break;
2671                 }
2672         }
2673
2674         if (cnt > limit) {
2675                 error << string_compose(_("There are already %1 recordings for %2, which I consider too many."), limit, ds.name()) << endmsg;
2676                 throw failed_constructor();
2677         }
2678
2679         /* we now have a unique name for the file, but figure out where to
2680            actually put it.
2681         */
2682
2683         string foo = buf;
2684
2685         spath = discover_best_sound_dir ();
2686
2687         string::size_type pos = foo.find_last_of ('/');
2688         
2689         if (pos == string::npos) {
2690                 spath += foo;
2691         } else {
2692                 spath += foo.substr (pos + 1);
2693         }
2694
2695         /* this might throw failed_constructor(), which is OK */
2696
2697         if (destructive) {
2698                 return new DestructiveFileSource (spath, frame_rate());
2699         } else {
2700                 return new FileSource (spath, frame_rate());
2701         }
2702 }
2703
2704 /* Playlist management */
2705
2706 Playlist *
2707 Session::get_playlist (string name)
2708 {
2709         Playlist* ret = 0;
2710
2711         if ((ret = playlist_by_name (name)) == 0) {
2712                 ret = new AudioPlaylist (*this, name);
2713         }
2714
2715         return ret;
2716 }
2717
2718 Playlist *
2719 Session::playlist_by_name (string name)
2720 {
2721         LockMonitor lm (playlist_lock, __LINE__, __FILE__);
2722         for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
2723                 if ((*i)->name() == name) {
2724                         return* i;
2725                 }
2726         }
2727         for (PlaylistList::iterator i = unused_playlists.begin(); i != unused_playlists.end(); ++i) {
2728                 if ((*i)->name() == name) {
2729                         return* i;
2730                 }
2731         }
2732         return 0;
2733 }
2734
2735 void
2736 Session::add_playlist (Playlist* playlist)
2737 {
2738         if (playlist->hidden()) {
2739                 return;
2740         }
2741
2742         { 
2743                 LockMonitor lm (playlist_lock, __LINE__, __FILE__);
2744                 if (find (playlists.begin(), playlists.end(), playlist) == playlists.end()) {
2745                         playlists.insert (playlists.begin(), playlist);
2746                         // playlist->ref();
2747                         playlist->InUse.connect (mem_fun (*this, &Session::track_playlist));
2748                         playlist->GoingAway.connect (mem_fun (*this, &Session::remove_playlist));
2749                 }
2750         }
2751
2752         set_dirty();
2753
2754         PlaylistAdded (playlist); /* EMIT SIGNAL */
2755 }
2756
2757 void
2758 Session::track_playlist (Playlist* pl, bool inuse)
2759 {
2760         PlaylistList::iterator x;
2761
2762         { 
2763                 LockMonitor lm (playlist_lock, __LINE__, __FILE__);
2764
2765                 if (!inuse) {
2766                         //cerr << "shifting playlist to unused: " << pl->name() << endl;
2767
2768                         unused_playlists.insert (pl);
2769                         
2770                         if ((x = playlists.find (pl)) != playlists.end()) {
2771                                 playlists.erase (x);
2772                         }
2773
2774                         
2775                 } else {
2776                         //cerr << "shifting playlist to used: " << pl->name() << endl;
2777                         
2778                         playlists.insert (pl);
2779                         
2780                         if ((x = unused_playlists.find (pl)) != unused_playlists.end()) {
2781                                 unused_playlists.erase (x);
2782                         }
2783                 }
2784         }
2785 }
2786
2787 void
2788 Session::remove_playlist (Playlist* playlist)
2789 {
2790         if (_state_of_the_state & Deletion) {
2791                 return;
2792         }
2793
2794         { 
2795                 LockMonitor lm (playlist_lock, __LINE__, __FILE__);
2796                 // cerr << "removing playlist: " << playlist->name() << endl;
2797
2798                 PlaylistList::iterator i;
2799
2800                 i = find (playlists.begin(), playlists.end(), playlist);
2801
2802                 if (i != playlists.end()) {
2803                         playlists.erase (i);
2804                 }
2805
2806                 i = find (unused_playlists.begin(), unused_playlists.end(), playlist);
2807                 if (i != unused_playlists.end()) {
2808                         unused_playlists.erase (i);
2809                 }
2810                 
2811         }
2812
2813         set_dirty();
2814
2815         PlaylistRemoved (playlist); /* EMIT SIGNAL */
2816 }
2817
2818 void 
2819 Session::set_audition (AudioRegion* r)
2820 {
2821         pending_audition_region = r;
2822         post_transport_work = PostTransportWork (post_transport_work | PostTransportAudition);
2823         schedule_butler_transport_work ();
2824 }
2825
2826 void
2827 Session::non_realtime_set_audition ()
2828 {
2829         if (pending_audition_region == (AudioRegion*) 0xfeedface) {
2830                 auditioner->audition_current_playlist ();
2831         } else if (pending_audition_region) {
2832                 auditioner->audition_region (*pending_audition_region);
2833         }
2834         pending_audition_region = 0;
2835         AuditionActive (true); /* EMIT SIGNAL */
2836 }
2837
2838 void
2839 Session::audition_playlist ()
2840 {
2841         Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
2842         ev->set_ptr ((void*) 0xfeedface);
2843         queue_event (ev);
2844 }
2845
2846 void
2847 Session::audition_region (AudioRegion& r)
2848 {
2849         Event* ev = new Event (Event::Audition, Event::Add, Event::Immediate, 0, 0.0);
2850         ev->set_ptr (&r);
2851         queue_event (ev);
2852 }
2853
2854 void
2855 Session::cancel_audition ()
2856 {
2857         if (auditioner->active()) {
2858                 auditioner->cancel_audition ();
2859                  AuditionActive (false); /* EMIT SIGNAL */
2860         }
2861 }
2862
2863 bool
2864 Session::RoutePublicOrderSorter::operator() (Route* a, Route* b)
2865 {
2866         return a->order_key(N_("signal")) < b->order_key(N_("signal"));
2867 }
2868
2869 void
2870 Session::remove_empty_sounds ()
2871 {
2872
2873         PathScanner scanner;
2874         string dir;
2875
2876         dir = sound_dir ();
2877
2878         vector<string *>* possible_audiofiles = scanner (dir, "\\.wav$", false, true);
2879         
2880         for (vector<string *>::iterator i = possible_audiofiles->begin(); i != possible_audiofiles->end(); ++i) {
2881
2882                 if (FileSource::is_empty (*(*i))) {
2883
2884                         unlink ((*i)->c_str());
2885                         
2886                         string peak_path = peak_path_from_audio_path (**i);
2887                         unlink (peak_path.c_str());
2888                 }
2889
2890                 delete* i;
2891         }
2892
2893         delete possible_audiofiles;
2894 }
2895
2896 bool
2897 Session::is_auditioning () const
2898 {
2899         /* can be called before we have an auditioner object */
2900         if (auditioner) {
2901                 return auditioner->active();
2902         } else {
2903                 return false;
2904         }
2905 }
2906
2907
2908 string
2909 Session::peak_path_from_audio_path (string audio_path)
2910 {
2911         /* XXX hardly bombproof! fix me */
2912
2913         string res;
2914
2915         res = PBD::dirname (audio_path);
2916         res = PBD::dirname (res);
2917         res += '/';
2918         res += peak_dir_name;
2919         res += '/';
2920         res += PBD::basename_nosuffix (audio_path);
2921         res += ".peak";
2922
2923         return res;
2924 }
2925
2926 string
2927 Session::old_peak_path_from_audio_path (string audio_path)
2928 {
2929         /* This is a hangover from when audio and peak files
2930            lived in the same directory. We need it to to 
2931            be able to open old sessions.
2932         */
2933
2934         /* XXX hardly bombproof! fix me */
2935
2936         string res = audio_path.substr (0, audio_path.find_last_of ('.'));
2937         res += ".peak";
2938         return res;
2939 }
2940
2941 void
2942 Session::set_all_solo (bool yn)
2943 {
2944         {
2945                 RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
2946                 
2947                 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2948                         if (!(*i)->hidden()) {
2949                                 (*i)->set_solo (yn, this);
2950                         }
2951                 }
2952         }
2953
2954         set_dirty();
2955 }
2956                 
2957 void
2958 Session::set_all_mute (bool yn)
2959 {
2960         {
2961                 RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
2962                 
2963                 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
2964                         if (!(*i)->hidden()) {
2965                                 (*i)->set_mute (yn, this);
2966                         }
2967                 }
2968         }
2969
2970         set_dirty();
2971 }
2972                 
2973 uint32_t
2974 Session::n_diskstreams () const
2975 {
2976         RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__);
2977         uint32_t n = 0;
2978
2979         for (DiskStreamList::const_iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2980                 if (!(*i)->hidden()) {
2981                         n++;
2982                 }
2983         }
2984         return n;
2985 }
2986
2987 void 
2988 Session::foreach_diskstream (void (DiskStream::*func)(void)) 
2989 {
2990         RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__);
2991         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
2992                 if (!(*i)->hidden()) {
2993                         ((*i)->*func)();
2994                 }
2995         }
2996 }
2997
2998 void
2999 Session::graph_reordered ()
3000 {
3001         /* don't do this stuff if we are setting up connections
3002            from a set_state() call.
3003         */
3004
3005         if (_state_of_the_state & InitialConnecting) {
3006                 return;
3007         }
3008
3009         RWLockMonitor lm1 (route_lock, true, __LINE__, __FILE__);
3010         RWLockMonitor lm2 (diskstream_lock, false, __LINE__, __FILE__);
3011
3012         resort_routes (0);
3013
3014         /* force all diskstreams to update their capture offset values to 
3015            reflect any changes in latencies within the graph.
3016         */
3017         
3018         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
3019                 (*i)->set_capture_offset ();
3020         }
3021 }
3022
3023 void
3024 Session::record_disenable_all ()
3025 {
3026         record_enable_change_all (false);
3027 }
3028
3029 void
3030 Session::record_enable_all ()
3031 {
3032         record_enable_change_all (true);
3033 }
3034
3035 void
3036 Session::record_enable_change_all (bool yn)
3037 {
3038         RWLockMonitor lm1 (route_lock, false, __LINE__, __FILE__);
3039         
3040         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
3041                 AudioTrack* at;
3042
3043                 if ((at = dynamic_cast<AudioTrack*>(*i)) != 0) {
3044                         at->set_record_enable (yn, this);
3045                 }
3046         }
3047         
3048         /* since we don't keep rec-enable state, don't mark session dirty */
3049 }
3050
3051 void
3052 Session::add_redirect (Redirect* redirect)
3053 {
3054         Send* send;
3055         Insert* insert;
3056         PortInsert* port_insert;
3057         PluginInsert* plugin_insert;
3058
3059         if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3060                 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3061                         _port_inserts.insert (_port_inserts.begin(), port_insert);
3062                 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3063                         _plugin_inserts.insert (_plugin_inserts.begin(), plugin_insert);
3064                 } else {
3065                         fatal << _("programming error: unknown type of Insert created!") << endmsg;
3066                         /*NOTREACHED*/
3067                 }
3068         } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3069                 _sends.insert (_sends.begin(), send);
3070         } else {
3071                 fatal << _("programming error: unknown type of Redirect created!") << endmsg;
3072                 /*NOTREACHED*/
3073         }
3074
3075         redirect->GoingAway.connect (mem_fun (*this, &Session::remove_redirect));
3076
3077         set_dirty();
3078 }
3079
3080 void
3081 Session::remove_redirect (Redirect* redirect)
3082 {
3083         Send* send;
3084         Insert* insert;
3085         PortInsert* port_insert;
3086         PluginInsert* plugin_insert;
3087
3088         if ((insert = dynamic_cast<Insert *> (redirect)) != 0) {
3089                 if ((port_insert = dynamic_cast<PortInsert *> (insert)) != 0) {
3090                         _port_inserts.remove (port_insert);
3091                 } else if ((plugin_insert = dynamic_cast<PluginInsert *> (insert)) != 0) {
3092                         _plugin_inserts.remove (plugin_insert);
3093                 } else {
3094                         fatal << _("programming error: unknown type of Insert deleted!") << endmsg;
3095                         /*NOTREACHED*/
3096                 }
3097         } else if ((send = dynamic_cast<Send *> (redirect)) != 0) {
3098                 _sends.remove (send);
3099         } else {
3100                 fatal << _("programming error: unknown type of Redirect deleted!") << endmsg;
3101                 /*NOTREACHED*/
3102         }
3103
3104         set_dirty();
3105 }
3106
3107 jack_nframes_t
3108 Session::available_capture_duration ()
3109 {
3110         const double scale = 4096.0 / sizeof (Sample);
3111         
3112         if (_total_free_4k_blocks * scale > (double) max_frames) {
3113                 return max_frames;
3114         }
3115         
3116         return (jack_nframes_t) floor (_total_free_4k_blocks * scale);
3117 }
3118
3119 void
3120 Session::add_connection (ARDOUR::Connection* connection)
3121 {
3122         {
3123                 LockMonitor (connection_lock, __LINE__, __FILE__);
3124                 _connections.push_back (connection);
3125         }
3126         
3127         ConnectionAdded (connection); /* EMIT SIGNAL */
3128
3129         set_dirty();
3130 }
3131
3132 void
3133 Session::remove_connection (ARDOUR::Connection* connection)
3134 {
3135         bool removed = false;
3136
3137         {
3138                 LockMonitor (connection_lock, __LINE__, __FILE__);
3139                 ConnectionList::iterator i = find (_connections.begin(), _connections.end(), connection);
3140                 
3141                 if (i != _connections.end()) {
3142                         _connections.erase (i);
3143                         removed = true;
3144                 }
3145         }
3146
3147         if (removed) {
3148                  ConnectionRemoved (connection); /* EMIT SIGNAL */
3149         }
3150
3151         set_dirty();
3152 }
3153
3154 ARDOUR::Connection *
3155 Session::connection_by_name (string name) const
3156 {
3157         LockMonitor lm (connection_lock, __LINE__, __FILE__);
3158
3159         for (ConnectionList::const_iterator i = _connections.begin(); i != _connections.end(); ++i) {
3160                 if ((*i)->name() == name) {
3161                         return* i;
3162                 }
3163         }
3164
3165         return 0;
3166 }
3167
3168 void
3169 Session::set_edit_mode (EditMode mode)
3170 {
3171         _edit_mode = mode;
3172         
3173         { 
3174                 LockMonitor lm (playlist_lock, __LINE__, __FILE__);
3175                 
3176                 for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) {
3177                         (*i)->set_edit_mode (mode);
3178                 }
3179         }
3180
3181         set_dirty ();
3182         ControlChanged (EditingMode); /* EMIT SIGNAL */
3183 }
3184
3185 void
3186 Session::tempo_map_changed (Change ignored)
3187 {
3188         clear_clicks ();
3189         set_dirty ();
3190 }
3191
3192 void
3193 Session::ensure_passthru_buffers (uint32_t howmany)
3194 {
3195         while (howmany > _passthru_buffers.size()) {
3196                 Sample *p;
3197 #ifdef NO_POSIX_MEMALIGN
3198                 p =  (Sample *) malloc(current_block_size * sizeof(Sample));
3199 #else
3200                 posix_memalign((void **)&p,16,current_block_size * 4);
3201 #endif                  
3202                 _passthru_buffers.push_back (p);
3203
3204                 *p = 0;
3205                 
3206 #ifdef NO_POSIX_MEMALIGN
3207                 p =  (Sample *) malloc(current_block_size * sizeof(Sample));
3208 #else
3209                 posix_memalign((void **)&p,16,current_block_size * 4);
3210 #endif                  
3211                 memset (p, 0, sizeof (Sample) * current_block_size);
3212                 _silent_buffers.push_back (p);
3213
3214         }
3215         allocate_pan_automation_buffers (current_block_size, howmany, false);
3216 }
3217
3218 string
3219 Session::next_send_name ()
3220 {
3221         char buf[32];
3222         snprintf (buf, sizeof (buf), "send %" PRIu32, ++send_cnt);
3223         return buf;
3224 }
3225
3226 string
3227 Session::next_insert_name ()
3228 {
3229         char buf[32];
3230         snprintf (buf, sizeof (buf), "insert %" PRIu32, ++insert_cnt);
3231         return buf;
3232 }
3233
3234 /* Named Selection management */
3235
3236 NamedSelection *
3237 Session::named_selection_by_name (string name)
3238 {
3239         LockMonitor lm (named_selection_lock, __LINE__, __FILE__);
3240         for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ++i) {
3241                 if ((*i)->name == name) {
3242                         return* i;
3243                 }
3244         }
3245         return 0;
3246 }
3247
3248 void
3249 Session::add_named_selection (NamedSelection* named_selection)
3250 {
3251         { 
3252                 LockMonitor lm (named_selection_lock, __LINE__, __FILE__);
3253                 named_selections.insert (named_selections.begin(), named_selection);
3254         }
3255
3256         set_dirty();
3257
3258          NamedSelectionAdded (); /* EMIT SIGNAL */
3259 }
3260
3261 void
3262 Session::remove_named_selection (NamedSelection* named_selection)
3263 {
3264         bool removed = false;
3265
3266         { 
3267                 LockMonitor lm (named_selection_lock, __LINE__, __FILE__);
3268
3269                 NamedSelectionList::iterator i = find (named_selections.begin(), named_selections.end(), named_selection);
3270
3271                 if (i != named_selections.end()) {
3272                         delete (*i);
3273                         named_selections.erase (i);
3274                         set_dirty();
3275                         removed = true;
3276                 }
3277         }
3278
3279         if (removed) {
3280                  NamedSelectionRemoved (); /* EMIT SIGNAL */
3281         }
3282 }
3283
3284 void
3285 Session::reset_native_file_format ()
3286 {
3287         // jlc - WHY take routelock?
3288         //RWLockMonitor lm1 (route_lock, true, __LINE__, __FILE__);
3289         RWLockMonitor lm2 (diskstream_lock, false, __LINE__, __FILE__);
3290
3291         for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) {
3292                 (*i)->reset_write_sources (false);
3293         }
3294 }
3295
3296 bool
3297 Session::route_name_unique (string n) const
3298 {
3299         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
3300         
3301         for (RouteList::const_iterator i = routes.begin(); i != routes.end(); ++i) {
3302                 if ((*i)->name() == n) {
3303                         return false;
3304                 }
3305         }
3306         
3307         return true;
3308 }
3309
3310 int
3311 Session::remove_file_source (FileSource& fs)
3312 {
3313         return fs.move_to_trash (dead_sound_dir_name);
3314 }
3315
3316 uint32_t
3317 Session::n_playlists () const
3318 {
3319         LockMonitor lm (playlist_lock, __LINE__, __FILE__);
3320         return playlists.size();
3321 }
3322
3323 void
3324 Session::set_solo_model (SoloModel sm)
3325 {
3326         if (sm != _solo_model) {
3327                 _solo_model = sm;
3328                 ControlChanged (SoloingModel);
3329                 set_dirty ();
3330         }
3331 }
3332
3333 void
3334 Session::allocate_pan_automation_buffers (jack_nframes_t nframes, uint32_t howmany, bool force)
3335 {
3336         if (!force && howmany <= _npan_buffers) {
3337                 return;
3338         }
3339
3340         if (_pan_automation_buffer) {
3341
3342                 for (uint32_t i = 0; i < _npan_buffers; ++i) {
3343                         delete [] _pan_automation_buffer[i];
3344                 }
3345
3346                 delete [] _pan_automation_buffer;
3347         }
3348
3349         _pan_automation_buffer = new pan_t*[howmany];
3350         
3351         for (uint32_t i = 0; i < howmany; ++i) {
3352                 _pan_automation_buffer[i] = new pan_t[nframes];
3353         }
3354
3355         _npan_buffers = howmany;
3356 }
3357
3358 void 
3359 Session::add_instant_xml (XMLNode& node, const std::string& dir)
3360 {
3361         Stateful::add_instant_xml (node, dir);
3362         Config->add_instant_xml (node, Config->get_user_ardour_path());
3363 }
3364
3365 int
3366 Session::freeze (InterThreadInfo& itt)
3367 {
3368         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
3369
3370         for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
3371
3372                 AudioTrack *at;
3373
3374                 if ((at = dynamic_cast<AudioTrack*>(*i)) != 0) {
3375                         /* XXX this is wrong because itt.progress will keep returning to zero at the start
3376                            of every track.
3377                         */
3378                         at->freeze (itt);
3379                 }
3380         }
3381
3382         return 0;
3383 }
3384
3385 int
3386 Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_t len,  bool overwrite, vector<Source*>& srcs,
3387                           InterThreadInfo& itt)
3388 {
3389         int ret = -1;
3390         Playlist* playlist;
3391         FileSource* fsource;
3392         uint32_t x;
3393         char buf[PATH_MAX+1];
3394         string dir;
3395         uint32_t nchans;
3396         jack_nframes_t position;
3397         jack_nframes_t this_chunk;
3398         jack_nframes_t to_do;
3399         vector<Sample*> buffers;
3400         const jack_nframes_t chunk_size = (256 * 1024)/4;
3401
3402         atomic_set (&processing_prohibited, 1);
3403         
3404         /* call tree *MUST* hold route_lock */
3405         
3406         if ((playlist = track.disk_stream().playlist()) == 0) {
3407                 goto out;
3408         }
3409
3410         /* external redirects will be a problem */
3411
3412         if (track.has_external_redirects()) {
3413                 goto out;
3414         }
3415
3416         nchans = track.disk_stream().n_channels();
3417         
3418         dir = discover_best_sound_dir ();
3419
3420         for (uint32_t chan_n=0; chan_n < nchans; ++chan_n) {
3421
3422                 for (x = 0; x < 99999; ++x) {
3423                         snprintf (buf, sizeof(buf), "%s/%s-%d-bounce-%" PRIu32 ".wav", dir.c_str(), playlist->name().c_str(), chan_n, x+1);
3424                         if (access (buf, F_OK) != 0) {
3425                                 break;
3426                         }
3427                 }
3428                 
3429                 if (x == 99999) {
3430                         error << string_compose (_("too many bounced versions of playlist \"%1\""), playlist->name()) << endmsg;
3431                         goto out;
3432                 }
3433                 
3434                 try {
3435                         fsource = new FileSource (buf, frame_rate());
3436                 }
3437                 
3438                 catch (failed_constructor& err) {
3439                         error << string_compose (_("cannot create new audio file \"%1\" for %2"), buf, track.name()) << endmsg;
3440                         goto out;
3441                 }
3442
3443                 srcs.push_back(fsource);
3444         }
3445
3446         /* XXX need to flush all redirects */
3447         
3448         position = start;
3449         to_do = len;
3450
3451         /* create a set of reasonably-sized buffers */
3452
3453         for (vector<Sample*>::iterator i = _passthru_buffers.begin(); i != _passthru_buffers.end(); ++i) {
3454                 Sample* b;
3455 #ifdef NO_POSIX_MEMALIGN
3456                 b =  (Sample *) malloc(chunk_size * sizeof(Sample));
3457 #else
3458                 posix_memalign((void **)&b,16,chunk_size * 4);
3459 #endif                  
3460                 buffers.push_back (b);
3461         }
3462         
3463         while (to_do && !itt.cancel) {
3464                 
3465                 this_chunk = min (to_do, chunk_size);
3466                 
3467                 if (track.export_stuff (buffers, nchans, start, this_chunk)) {
3468                         goto out;
3469                 }
3470
3471                 uint32_t n = 0;
3472                 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) {
3473                         if ((*src)->write (buffers[n], this_chunk) != this_chunk) {
3474                                 goto out;
3475                         }
3476                 }
3477                 
3478                 start += this_chunk;
3479                 to_do -= this_chunk;
3480                 
3481                 itt.progress = (float) (1.0 - ((double) to_do / len));
3482
3483         }
3484
3485         if (!itt.cancel) {
3486                 
3487                 time_t now;
3488                 struct tm* xnow;
3489                 time (&now);
3490                 xnow = localtime (&now);
3491                 
3492                 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3493                         dynamic_cast<FileSource*>((*src))->update_header (position, *xnow, now);
3494                 }
3495                 
3496                 /* build peakfile for new source */
3497                 
3498                 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3499                         dynamic_cast<FileSource*>(*src)->build_peaks ();
3500                 }
3501                 
3502                 ret = 0;
3503         }
3504                 
3505   out:
3506         if (ret) {
3507                 for (vector<Source*>::iterator src=srcs.begin(); src != srcs.end(); ++src) {
3508                         dynamic_cast<FileSource*>(*src)->mark_for_remove ();
3509                         delete *src;
3510                 }
3511         }
3512
3513         for (vector<Sample*>::iterator i = buffers.begin(); i != buffers.end(); ++i) {
3514                 free(*i);
3515         }
3516
3517         atomic_set (&processing_prohibited, 0);
3518
3519         itt.done = true;
3520
3521         return ret;
3522 }
3523
3524 vector<Sample*>&
3525 Session::get_silent_buffers (uint32_t howmany)
3526 {
3527         for (uint32_t i = 0; i < howmany; ++i) {
3528                 memset (_silent_buffers[i], 0, sizeof (Sample) * current_block_size);
3529         }
3530         return _silent_buffers;
3531 }
3532
3533 uint32_t 
3534 Session::ntracks () const
3535 {
3536         uint32_t n = 0;
3537         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
3538
3539         for (RouteList::const_iterator i = routes.begin(); i != routes.end(); ++i) {
3540                 if (dynamic_cast<AudioTrack*> (*i)) {
3541                         ++n;
3542                 }
3543         }
3544
3545         return n;
3546 }
3547
3548 uint32_t 
3549 Session::nbusses () const
3550 {
3551         uint32_t n = 0;
3552         RWLockMonitor lm (route_lock, false, __LINE__, __FILE__);
3553
3554         for (RouteList::const_iterator i = routes.begin(); i != routes.end(); ++i) {
3555                 if (dynamic_cast<AudioTrack*> (*i) == 0) {
3556                         ++n;
3557                 }
3558         }
3559
3560         return n;
3561 }
3562
3563 void
3564 Session::set_layer_model (LayerModel lm)
3565 {
3566         if (lm != layer_model) {
3567                 layer_model = lm;
3568                 set_dirty ();
3569                 ControlChanged (LayeringModel);
3570         }
3571 }
3572
3573 void
3574 Session::set_xfade_model (CrossfadeModel xm)
3575 {
3576         if (xm != xfade_model) {
3577                 xfade_model = xm;
3578                 set_dirty ();
3579                 ControlChanged (CrossfadingModel);
3580         }
3581 }
3582