On second though, just remove that define entirely.
[ardour.git] / libs / ardour / session_transport.cc
1 /*
2     Copyright (C) 1999-2003 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 */
19
20 #include <cmath>
21 #include <cerrno>
22 #include <unistd.h>
23
24 #include <sigc++/bind.h>
25 #include <sigc++/retype.h>
26
27 #include "pbd/undo.h"
28 #include "pbd/error.h"
29 #include <glibmm/thread.h>
30 #include "pbd/pthread_utils.h"
31 #include "pbd/memento_command.h"
32 #include "pbd/stacktrace.h"
33
34 #include "midi++/mmc.h"
35 #include "midi++/port.h"
36
37 #include "ardour/ardour.h"
38 #include "ardour/audio_diskstream.h"
39 #include "ardour/audioengine.h"
40 #include "ardour/auditioner.h"
41 #include "ardour/butler.h"
42 #include "ardour/location.h"
43 #include "ardour/session.h"
44 #include "ardour/slave.h"
45
46 #include "i18n.h"
47
48 using namespace std;
49 using namespace ARDOUR;
50 using namespace sigc;
51 using namespace PBD;
52
53 void
54 Session::request_input_change_handling ()
55 {
56         if (!(_state_of_the_state & (InitialConnecting|Deletion))) {
57                 Event* ev = new Event (Event::InputConfigurationChange, Event::Add, Event::Immediate, 0, 0.0);
58                 queue_event (ev);
59         }
60 }
61
62 void
63 Session::request_slave_source (SlaveSource src)
64 {
65         Event* ev = new Event (Event::SetSlaveSource, Event::Add, Event::Immediate, 0, 0.0);
66
67         if (src == JACK) {
68                 /* could set_seamless_loop() be disposed of entirely?*/
69                 Config->set_seamless_loop (false);
70         } else {
71                 Config->set_seamless_loop (true);
72         }
73         ev->slave = src;
74         queue_event (ev);
75 }
76
77 void
78 Session::request_transport_speed (double speed)
79 {
80         Event* ev = new Event (Event::SetTransportSpeed, Event::Add, Event::Immediate, 0, speed);
81         queue_event (ev);
82 }
83
84 void
85 Session::request_diskstream_speed (Diskstream& ds, double speed)
86 {
87         Event* ev = new Event (Event::SetDiskstreamSpeed, Event::Add, Event::Immediate, 0, speed);
88         ev->set_ptr (&ds);
89         queue_event (ev);
90 }
91
92 void
93 Session::request_stop (bool abort)
94 {
95         Event* ev = new Event (Event::SetTransportSpeed, Event::Add, Event::Immediate, 0, 0.0, abort);
96         queue_event (ev);
97 }
98
99 void
100 Session::request_locate (nframes_t target_frame, bool with_roll)
101 {
102         Event *ev = new Event (with_roll ? Event::LocateRoll : Event::Locate, Event::Add, Event::Immediate, target_frame, 0, false);
103         queue_event (ev);
104 }
105
106 void
107 Session::force_locate (nframes_t target_frame, bool with_roll)
108 {
109         Event *ev = new Event (with_roll ? Event::LocateRoll : Event::Locate, Event::Add, Event::Immediate, target_frame, 0, true);
110         queue_event (ev);
111 }
112
113 void
114 Session::request_play_loop (bool yn)
115 {
116         Event* ev;
117         Location *location = _locations.auto_loop_location();
118
119         if (location == 0 && yn) {
120                 error << _("Cannot loop - no loop range defined")
121                       << endmsg;
122                 return;
123         }
124
125         ev = new Event (Event::SetLoop, Event::Add, Event::Immediate, 0, 0.0, yn);
126         queue_event (ev);
127
128         if (!yn && Config->get_seamless_loop() && transport_rolling()) {
129                 // request an immediate locate to refresh the diskstreams
130                 // after disabling looping
131                 request_locate (_transport_frame-1, false);
132         }
133 }
134
135 void
136 Session::realtime_stop (bool abort)
137 {
138         /* assume that when we start, we'll be moving forwards */
139
140         // FIXME: where should this really be? [DR]
141         //send_full_time_code();
142         deliver_mmc (MIDI::MachineControl::cmdStop, 0);
143         deliver_mmc (MIDI::MachineControl::cmdLocate, _transport_frame);
144
145         if (_transport_speed < 0.0f) {
146                 post_transport_work = PostTransportWork (post_transport_work | PostTransportStop | PostTransportReverse);
147         } else {
148                 post_transport_work = PostTransportWork (post_transport_work | PostTransportStop);
149         }
150
151         if (actively_recording()) {
152
153                 /* move the transport position back to where the
154                    request for a stop was noticed. we rolled
155                    past that point to pick up delayed input.
156                 */
157
158                 decrement_transport_position (_worst_output_latency);
159
160                 /* the duration change is not guaranteed to have happened, but is likely */
161
162                 post_transport_work = PostTransportWork (post_transport_work | PostTransportDuration);
163         }
164
165         if (abort) {
166                 post_transport_work = PostTransportWork (post_transport_work | PostTransportAbort);
167         }
168
169         _clear_event_type (Event::StopOnce);
170         _clear_event_type (Event::RangeStop);
171         _clear_event_type (Event::RangeLocate);
172
173         disable_record (true);
174
175         reset_slave_state ();
176
177         _transport_speed = 0;
178         _target_transport_speed = 0;
179
180         if (config.get_use_video_sync()) {
181                 waiting_for_sync_offset = true;
182         }
183
184         transport_sub_state = ((Config->get_slave_source() == None && config.get_auto_return()) ? AutoReturning : 0);
185 }
186
187 void
188 Session::butler_transport_work ()
189 {
190   restart:
191         bool finished;
192         boost::shared_ptr<RouteList> r = routes.reader ();
193         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
194
195         int on_entry = g_atomic_int_get (&_butler->should_do_transport_work);
196         finished = true;
197
198         if (post_transport_work & PostTransportCurveRealloc) {
199                 for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
200                         (*i)->curve_reallocate();
201                 }
202         }
203
204         if (post_transport_work & PostTransportInputChange) {
205                 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
206                         (*i)->non_realtime_input_change ();
207                 }
208         }
209
210         if (post_transport_work & PostTransportSpeed) {
211                 non_realtime_set_speed ();
212         }
213
214         if (post_transport_work & PostTransportReverse) {
215
216                 clear_clicks();
217                 cumulative_rf_motion = 0;
218                 reset_rf_scale (0);
219
220                 /* don't seek if locate will take care of that in non_realtime_stop() */
221
222                 if (!(post_transport_work & PostTransportLocate)) {
223
224                         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
225                                 if (!(*i)->hidden()) {
226                                         (*i)->non_realtime_locate (_transport_frame);
227                                 }
228                                 if (on_entry != g_atomic_int_get (&_butler->should_do_transport_work)) {
229                                         /* new request, stop seeking, and start again */
230                                         g_atomic_int_dec_and_test (&_butler->should_do_transport_work);
231                                         goto restart;
232                                 }
233                         }
234                 }
235         }
236
237         if (post_transport_work & PostTransportLocate) {
238                 non_realtime_locate ();
239         }
240
241         if (post_transport_work & PostTransportStop) {
242                 non_realtime_stop (post_transport_work & PostTransportAbort, on_entry, finished);
243                 if (!finished) {
244                         g_atomic_int_dec_and_test (&_butler->should_do_transport_work);
245                         goto restart;
246                 }
247         }
248
249         if (post_transport_work & PostTransportOverWrite) {
250                 non_realtime_overwrite (on_entry, finished);
251                 if (!finished) {
252                         g_atomic_int_dec_and_test (&_butler->should_do_transport_work);
253                         goto restart;
254                 }
255         }
256
257         if (post_transport_work & PostTransportAudition) {
258                 non_realtime_set_audition ();
259         }
260
261         g_atomic_int_dec_and_test (&_butler->should_do_transport_work);
262 }
263
264 void
265 Session::non_realtime_set_speed ()
266 {
267         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
268
269         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
270                 (*i)->non_realtime_set_speed ();
271         }
272 }
273
274 void
275 Session::non_realtime_overwrite (int on_entry, bool& finished)
276 {
277         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
278
279         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
280                 if ((*i)->pending_overwrite) {
281                         (*i)->overwrite_existing_buffers ();
282                 }
283                 if (on_entry != g_atomic_int_get (&_butler->should_do_transport_work)) {
284                         finished = false;
285                         return;
286                 }
287         }
288 }
289
290
291 void
292 Session::non_realtime_locate ()
293 {
294         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
295
296         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
297                 (*i)->non_realtime_locate (_transport_frame);
298         }
299 }
300
301
302 void
303 Session::non_realtime_stop (bool abort, int on_entry, bool& finished)
304 {
305         struct tm* now;
306         time_t     xnow;
307         bool       did_record;
308         bool       saved;
309
310         did_record = false;
311         saved = false;
312
313         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
314
315         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
316                 if ((*i)->get_captured_frames () != 0) {
317                         did_record = true;
318                         break;
319                 }
320         }
321
322         /* stop and locate are merged here because they share a lot of common stuff */
323
324         time (&xnow);
325         now = localtime (&xnow);
326
327         if (auditioner) {
328                 auditioner->cancel_audition ();
329         }
330
331         clear_clicks();
332         cumulative_rf_motion = 0;
333         reset_rf_scale (0);
334
335         if (did_record) {
336                 begin_reversible_command ("capture");
337
338                 Location* loc = _locations.end_location();
339                 bool change_end = false;
340
341                 if (_transport_frame < loc->end()) {
342
343                         /* stopped recording before current end */
344
345                         if (config.get_end_marker_is_free()) {
346
347                                 /* first capture for this session, move end back to where we are */
348
349                                 change_end = true;
350                         }
351
352                 } else if (_transport_frame > loc->end()) {
353
354                         /* stopped recording after the current end, extend it */
355
356                         change_end = true;
357                 }
358
359                 if (change_end) {
360                         XMLNode &before = loc->get_state();
361                         loc->set_end(_transport_frame);
362                         XMLNode &after = loc->get_state();
363                         add_command (new MementoCommand<Location>(*loc, &before, &after));
364                 }
365
366                 config.set_end_marker_is_free (false);
367                 _have_captured = true;
368         }
369
370         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
371                 (*i)->transport_stopped (*now, xnow, abort);
372         }
373
374         boost::shared_ptr<RouteList> r = routes.reader ();
375
376         for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
377                 if (!(*i)->is_hidden()) {
378                         (*i)->set_pending_declick (0);
379                 }
380         }
381
382         if (did_record) {
383                 commit_reversible_command ();
384         }
385
386         if (_engine.running()) {
387                 update_latency_compensation (true, abort);
388         }
389
390         bool const auto_return_enabled =
391                 (Config->get_slave_source() == None && config.get_auto_return());
392
393         if (auto_return_enabled ||
394             (post_transport_work & PostTransportLocate) ||
395             (_requested_return_frame >= 0) ||
396             synced_to_jack()) {
397
398                 if (pending_locate_flush) {
399                         flush_all_inserts ();
400                 }
401
402                 if ((auto_return_enabled || synced_to_jack() || _requested_return_frame >= 0) &&
403                     !(post_transport_work & PostTransportLocate)) {
404
405                         bool do_locate = false;
406
407                         if (_requested_return_frame >= 0) {
408                                 _transport_frame = _requested_return_frame;
409                                 _requested_return_frame = -1;
410                                 do_locate = true;
411                         } else {
412                                 _transport_frame = _last_roll_location;
413                         }
414
415                         if (synced_to_jack() && !play_loop) {
416                                 do_locate = true;
417                         }
418
419                         if (do_locate) {
420                                 // cerr << "non-realtimestop: transport locate to " << _transport_frame << endl;
421                                 _engine.transport_locate (_transport_frame);
422                         }
423                 }
424
425         }
426
427         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
428                 if (!(*i)->hidden()) {
429                         (*i)->non_realtime_locate (_transport_frame);
430                 }
431                 if (on_entry != g_atomic_int_get (&_butler->should_do_transport_work)) {
432                         finished = false;
433                         /* we will be back */
434                         return;
435                 }
436         }
437
438         have_looped = false;
439
440         send_full_time_code (0);
441         deliver_mmc (MIDI::MachineControl::cmdStop, 0);
442         deliver_mmc (MIDI::MachineControl::cmdLocate, _transport_frame);
443
444         if (did_record) {
445
446                 /* XXX its a little odd that we're doing this here
447                    when realtime_stop(), which has already executed,
448                    will have done this.
449                    JLC - so let's not because it seems unnecessary and breaks loop record
450                 */
451 #if 0
452                 if (!Config->get_latched_record_enable()) {
453                         g_atomic_int_set (&_record_status, Disabled);
454                 } else {
455                         g_atomic_int_set (&_record_status, Enabled);
456                 }
457                 RecordStateChanged (); /* emit signal */
458 #endif
459         }
460
461         if ((post_transport_work & PostTransportLocate) && get_record_enabled()) {
462                 /* capture start has been changed, so save pending state */
463                 save_state ("", true);
464                 saved = true;
465         }
466
467         /* always try to get rid of this */
468
469         remove_pending_capture_state ();
470
471         /* save the current state of things if appropriate */
472
473         if (did_record && !saved) {
474                 save_state (_current_snapshot_name);
475         }
476
477         if (post_transport_work & PostTransportDuration) {
478                 DurationChanged (); /* EMIT SIGNAL */
479         }
480
481         if (post_transport_work & PostTransportStop) {
482                 _play_range = false;
483
484                 /* do not turn off autoloop on stop */
485
486         }
487
488         nframes_t tf = _transport_frame;
489
490         PositionChanged (tf); /* EMIT SIGNAL */
491         TransportStateChange (); /* EMIT SIGNAL */
492
493         /* and start it up again if relevant */
494
495         if ((post_transport_work & PostTransportLocate) && Config->get_slave_source() == None && pending_locate_roll) {
496                 request_transport_speed (1.0);
497                 pending_locate_roll = false;
498         }
499 }
500
501 void
502 Session::check_declick_out ()
503 {
504         bool locate_required = transport_sub_state & PendingLocate;
505
506         /* this is called after a process() iteration. if PendingDeclickOut was set,
507            it means that we were waiting to declick the output (which has just been
508            done) before doing something else. this is where we do that "something else".
509
510            note: called from the audio thread.
511         */
512
513         if (transport_sub_state & PendingDeclickOut) {
514
515                 if (locate_required) {
516                         start_locate (pending_locate_frame, pending_locate_roll, pending_locate_flush);
517                         transport_sub_state &= ~(PendingDeclickOut|PendingLocate);
518                 } else {
519                         stop_transport (pending_abort);
520                         transport_sub_state &= ~(PendingDeclickOut|PendingLocate);
521                 }
522         }
523 }
524
525 void
526 Session::set_play_loop (bool yn)
527 {
528         /* Called from event-handling context */
529
530         if ((actively_recording() && yn) || _locations.auto_loop_location() == 0) {
531                 return;
532         }
533
534         set_dirty();
535
536         if (yn && Config->get_seamless_loop() && synced_to_jack()) {
537                 warning << _("Seamless looping cannot be supported while Ardour is using JACK transport.\n"
538                              "Recommend changing the configured options")
539                         << endmsg;
540                 return;
541         }
542
543
544         if ((play_loop = yn)) {
545
546                 Location *loc;
547
548
549                 if ((loc = _locations.auto_loop_location()) != 0) {
550
551                         if (Config->get_seamless_loop()) {
552                                 // set all diskstreams to use internal looping
553                                 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
554                                 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
555                                         if (!(*i)->hidden()) {
556                                                 (*i)->set_loop (loc);
557                                         }
558                                 }
559                         }
560                         else {
561                                 // set all diskstreams to NOT use internal looping
562                                 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
563                                 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
564                                         if (!(*i)->hidden()) {
565                                                 (*i)->set_loop (0);
566                                         }
567                                 }
568                         }
569
570                         /* stick in the loop event */
571
572                         Event* event = new Event (Event::AutoLoop, Event::Replace, loc->end(), loc->start(), 0.0f);
573                         merge_event (event);
574
575                         /* locate to start of loop and roll if current pos is outside of the loop range */
576                         if (_transport_frame < loc->start() || _transport_frame > loc->end()) {
577                                 event = new Event (Event::LocateRoll, Event::Add, Event::Immediate, loc->start(), 0, !synced_to_jack());
578                                 merge_event (event);
579                         }
580                         else {
581                                 // locate to current position (+ 1 to force reload)
582                                 event = new Event (Event::LocateRoll, Event::Add, Event::Immediate, _transport_frame + 1, 0, !synced_to_jack());
583                                 merge_event (event);
584                         }
585                 }
586
587
588
589         } else {
590                 clear_events (Event::AutoLoop);
591
592                 // set all diskstreams to NOT use internal looping
593                 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
594                 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
595                         if (!(*i)->hidden()) {
596                                 (*i)->set_loop (0);
597                         }
598                 }
599
600         }
601 }
602
603 void
604 Session::flush_all_inserts ()
605 {
606         boost::shared_ptr<RouteList> r = routes.reader ();
607
608         for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
609                 (*i)->flush_processors ();
610         }
611 }
612
613 void
614 Session::start_locate (nframes_t target_frame, bool with_roll, bool with_flush, bool with_loop)
615 {
616         if (synced_to_jack()) {
617
618                 double sp;
619                 nframes_t pos;
620
621                 _slave->speed_and_position (sp, pos);
622
623                 if (target_frame != pos) {
624
625                         /* tell JACK to change transport position, and we will
626                            follow along later in ::follow_slave()
627                         */
628
629                         _engine.transport_locate (target_frame);
630
631                         if (sp != 1.0f && with_roll) {
632                                 _engine.transport_start ();
633                         }
634
635                 }
636
637         } else {
638                 locate (target_frame, with_roll, with_flush, with_loop);
639         }
640 }
641
642 int
643 Session::micro_locate (nframes_t distance)
644 {
645         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
646
647         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
648                 if (!(*i)->can_internal_playback_seek (distance)) {
649                         return -1;
650                 }
651         }
652
653         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
654                 (*i)->internal_playback_seek (distance);
655         }
656
657         _transport_frame += distance;
658         return 0;
659 }
660
661 void
662 Session::locate (nframes_t target_frame, bool with_roll, bool with_flush, bool with_loop)
663 {
664         if (actively_recording() && !with_loop) {
665                 return;
666         }
667
668         if (_transport_frame == target_frame && !loop_changing && !with_loop) {
669                 if (with_roll) {
670                         set_transport_speed (1.0, false);
671                 }
672                 loop_changing = false;
673                 return;
674         }
675
676         // Update Timecode time
677         // [DR] FIXME: find out exactly where this should go below
678         _transport_frame = target_frame;
679         timecode_time(_transport_frame, transmitting_timecode_time);
680         outbound_mtc_timecode_frame = _transport_frame;
681         next_quarter_frame_to_send = 0;
682
683         if (_transport_speed && (!with_loop || loop_changing)) {
684                 /* schedule a declick. we'll be called again when its done */
685
686                 if (!(transport_sub_state & PendingDeclickOut)) {
687                         transport_sub_state |= (PendingDeclickOut|PendingLocate);
688                         pending_locate_frame = target_frame;
689                         pending_locate_roll = with_roll;
690                         pending_locate_flush = with_flush;
691                         return;
692                 }
693         }
694
695         if (transport_rolling() && (!auto_play_legal || !config.get_auto_play()) && !with_roll && !(synced_to_jack() && play_loop)) {
696                 realtime_stop (false);
697         }
698
699         if ( !with_loop || loop_changing) {
700
701                 post_transport_work = PostTransportWork (post_transport_work | PostTransportLocate);
702
703                 if (with_roll) {
704                         post_transport_work = PostTransportWork (post_transport_work | PostTransportRoll);
705                 }
706
707                 _butler->schedule_transport_work ();
708
709         } else {
710
711                 /* this is functionally what clear_clicks() does but with a tentative lock */
712
713                 Glib::RWLock::WriterLock clickm (click_lock, Glib::TRY_LOCK);
714
715                 if (clickm.locked()) {
716
717                         for (Clicks::iterator i = clicks.begin(); i != clicks.end(); ++i) {
718                                 delete *i;
719                         }
720
721                         clicks.clear ();
722                 }
723         }
724
725         if (with_roll) {
726                 /* switch from input if we're going to roll */
727                 if (Config->get_monitoring_model() == HardwareMonitoring) {
728
729                         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
730
731                         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
732                                 if ((*i)->record_enabled ()) {
733                                         //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
734                                         (*i)->monitor_input (!config.get_auto_input());
735                                 }
736                         }
737                 }
738         } else {
739                 /* otherwise we're going to stop, so do the opposite */
740                 if (Config->get_monitoring_model() == HardwareMonitoring) {
741                         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
742
743                         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
744                                 if ((*i)->record_enabled ()) {
745                                         //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl;
746                                         (*i)->monitor_input (true);
747                                 }
748                         }
749                 }
750         }
751
752         /* cancel looped playback if transport pos outside of loop range */
753         if (play_loop) {
754                 Location* al = _locations.auto_loop_location();
755
756                 if (al && (_transport_frame < al->start() || _transport_frame > al->end())) {
757                         // cancel looping directly, this is called from event handling context
758                         set_play_loop (false);
759                 }
760                 else if (al && _transport_frame == al->start()) {
761                         if (with_loop) {
762                                 // this is only necessary for seamless looping
763
764                                 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
765
766                                 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
767                                         if ((*i)->record_enabled ()) {
768                                                 // tell it we've looped, so it can deal with the record state
769                                                 (*i)->transport_looped(_transport_frame);
770                                         }
771                                 }
772                         }
773                         have_looped = true;
774                         TransportLooped(); // EMIT SIGNAL
775                 }
776         }
777
778         loop_changing = false;
779
780         _send_timecode_update = true;
781
782         Located (); /* EMIT SIGNAL */
783 }
784
785 /** Set the transport speed.
786  * @param speed New speed
787  * @param abort
788  */
789 void
790 Session::set_transport_speed (double speed, bool abort)
791 {
792         if (_transport_speed == speed) {
793                 return;
794         }
795
796         _target_transport_speed = fabs(speed);
797
798         /* 8.0 max speed is somewhat arbitrary but based on guestimates regarding disk i/o capability
799            and user needs. We really need CD-style "skip" playback for ffwd and rewind.
800         */
801
802         if (speed > 0) {
803                 speed = min (8.0, speed);
804         } else if (speed < 0) {
805                 speed = max (-8.0, speed);
806         }
807
808         if (transport_rolling() && speed == 0.0) {
809
810                 /* we are rolling and we want to stop */
811
812                 if (Config->get_monitoring_model() == HardwareMonitoring)
813                 {
814                         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
815
816                         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
817                                 if ((*i)->record_enabled ()) {
818                                         //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl;
819                                         (*i)->monitor_input (true);
820                                 }
821                         }
822                 }
823
824                 if (synced_to_jack ()) {
825                         _engine.transport_stop ();
826                 } else {
827                         stop_transport (abort);
828                 }
829
830         } else if (transport_stopped() && speed == 1.0) {
831
832                 /* we are stopped and we want to start rolling at speed 1 */
833
834                 if (!get_record_enabled() && Config->get_stop_at_session_end() && _transport_frame >= current_end_frame()) {
835                         return;
836                 }
837
838                 if (Config->get_monitoring_model() == HardwareMonitoring) {
839
840                         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
841
842                         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
843                                 if (config.get_auto_input() && (*i)->record_enabled ()) {
844                                         //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl;
845                                         (*i)->monitor_input (false);
846                                 }
847                         }
848                 }
849
850                 if (synced_to_jack()) {
851                         _engine.transport_start ();
852                 } else {
853                         start_transport ();
854                 }
855
856         } else {
857
858                 if (!get_record_enabled() && Config->get_stop_at_session_end() && _transport_frame >= current_end_frame()) {
859                         return;
860                 }
861
862                 if ((synced_to_jack()) && speed != 0.0 && speed != 1.0) {
863                         warning << _("Global varispeed cannot be supported while Ardour is connected to JACK transport control")
864                                 << endmsg;
865                         return;
866                 }
867
868                 if (actively_recording()) {
869                         return;
870                 }
871
872                 if (speed > 0.0 && _transport_frame == current_end_frame()) {
873                         return;
874                 }
875
876                 if (speed < 0.0 && _transport_frame == 0) {
877                         return;
878                 }
879
880                 clear_clicks ();
881
882                 /* if we are reversing relative to the current speed, or relative to the speed
883                    before the last stop, then we have to do extra work.
884                 */
885
886                 if ((_transport_speed && speed * _transport_speed < 0.0) || (_last_transport_speed * speed < 0.0) || (_last_transport_speed == 0.0f && speed < 0.0f)) {
887                         post_transport_work = PostTransportWork (post_transport_work | PostTransportReverse);
888                 }
889
890                 _last_transport_speed = _transport_speed;
891                 _transport_speed = speed;
892
893                 boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
894                 for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
895                         if ((*i)->realtime_set_speed ((*i)->speed(), true)) {
896                                 post_transport_work = PostTransportWork (post_transport_work | PostTransportSpeed);
897                         }
898                 }
899
900                 if (post_transport_work & (PostTransportSpeed|PostTransportReverse)) {
901                         _butler->schedule_transport_work ();
902                 }
903         }
904 }
905
906
907 /** Stop the transport.  */
908 void
909 Session::stop_transport (bool abort)
910 {
911         if (_transport_speed == 0.0f) {
912                 return;
913         }
914
915         if (actively_recording() && !(transport_sub_state & StopPendingCapture) &&
916             _worst_output_latency > current_block_size)
917         {
918
919                 /* we need to capture the audio that has still not yet been received by the system
920                    at the time the stop is requested, so we have to roll past that time.
921
922                    we want to declick before stopping, so schedule the autostop for one
923                    block before the actual end. we'll declick in the subsequent block,
924                    and then we'll really be stopped.
925                 */
926
927                 Event *ev = new Event (Event::StopOnce, Event::Replace,
928                                        _transport_frame + _worst_output_latency - current_block_size,
929                                        0, 0, abort);
930
931                 merge_event (ev);
932                 transport_sub_state |= StopPendingCapture;
933                 pending_abort = abort;
934                 return;
935         }
936
937
938         if ((transport_sub_state & PendingDeclickOut) == 0) {
939                 transport_sub_state |= PendingDeclickOut;
940                 /* we'll be called again after the declick */
941                 pending_abort = abort;
942                 return;
943         }
944
945         realtime_stop (abort);
946         _butler->schedule_transport_work ();
947 }
948
949 void
950 Session::start_transport ()
951 {
952         _last_roll_location = _transport_frame;
953         have_looped = false;
954
955         /* if record status is Enabled, move it to Recording. if its
956            already Recording, move it to Disabled.
957         */
958
959         switch (record_status()) {
960         case Enabled:
961                 if (!config.get_punch_in()) {
962                         enable_record ();
963                 }
964                 break;
965
966         case Recording:
967                 if (!play_loop) {
968                         disable_record (false);
969                 }
970                 break;
971
972         default:
973                 break;
974         }
975
976         transport_sub_state |= PendingDeclickIn;
977
978         _transport_speed = 1.0;
979         _target_transport_speed = 1.0;
980
981         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
982         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
983                 (*i)->realtime_set_speed ((*i)->speed(), true);
984         }
985
986         deliver_mmc(MIDI::MachineControl::cmdDeferredPlay, _transport_frame);
987
988         TransportStateChange (); /* EMIT SIGNAL */
989 }
990
991 /** Do any transport work in the audio thread that needs to be done after the
992  * transport thread is finished.  Audio thread, realtime safe.
993  */
994 void
995 Session::post_transport ()
996 {
997         if (post_transport_work & PostTransportAudition) {
998                 if (auditioner && auditioner->active()) {
999                         process_function = &Session::process_audition;
1000                 } else {
1001                         process_function = &Session::process_with_events;
1002                 }
1003         }
1004
1005         if (post_transport_work & PostTransportStop) {
1006
1007                 transport_sub_state = 0;
1008         }
1009
1010         if (post_transport_work & PostTransportLocate) {
1011
1012                 if (((Config->get_slave_source() == None && (auto_play_legal && config.get_auto_play())) && !_exporting) || (post_transport_work & PostTransportRoll)) {
1013                         start_transport ();
1014
1015                 } else {
1016                         transport_sub_state = 0;
1017                 }
1018         }
1019
1020         set_next_event ();
1021
1022         post_transport_work = PostTransportWork (0);
1023 }
1024
1025 void
1026 Session::reset_rf_scale (nframes_t motion)
1027 {
1028         cumulative_rf_motion += motion;
1029
1030         if (cumulative_rf_motion < 4 * _current_frame_rate) {
1031                 rf_scale = 1;
1032         } else if (cumulative_rf_motion < 8 * _current_frame_rate) {
1033                 rf_scale = 4;
1034         } else if (cumulative_rf_motion < 16 * _current_frame_rate) {
1035                 rf_scale = 10;
1036         } else {
1037                 rf_scale = 100;
1038         }
1039
1040         if (motion != 0) {
1041                 set_dirty();
1042         }
1043 }
1044
1045 void
1046 Session::set_slave_source (SlaveSource src)
1047 {
1048         bool reverse = false;
1049         bool non_rt_required = false;
1050
1051         if (_transport_speed) {
1052                 error << _("please stop the transport before adjusting slave settings") << endmsg;
1053                 return;
1054         }
1055
1056 //      if (src == JACK && Config->get_jack_time_master()) {
1057 //              return;
1058 //      }
1059
1060         delete _slave;
1061         _slave = 0;
1062
1063         if (_transport_speed < 0.0) {
1064                 reverse = true;
1065         }
1066
1067         switch (src) {
1068         case None:
1069                 stop_transport ();
1070                 break;
1071
1072         case MTC:
1073                 if (_mtc_port) {
1074                         try {
1075                                 _slave = new MTC_Slave (*this, *_mtc_port);
1076                         }
1077
1078                         catch (failed_constructor& err) {
1079                                 return;
1080                         }
1081
1082                 } else {
1083                         error << _("No MTC port defined: MTC slaving is impossible.") << endmsg;
1084                         return;
1085                 }
1086                 break;
1087
1088         case MIDIClock:
1089                 if (_midi_clock_port) {
1090                         try {
1091                                 _slave = new MIDIClock_Slave (*this, *_midi_clock_port, 24);
1092                         }
1093
1094                         catch (failed_constructor& err) {
1095                                 return;
1096                         }
1097
1098                 } else {
1099                         error << _("No MIDI Clock port defined: MIDI Clock slaving is impossible.") << endmsg;
1100                         return;
1101                 }
1102                 break;
1103
1104         case JACK:
1105                 _slave = new JACK_Slave (_engine.jack());
1106                 break;
1107
1108         };
1109
1110         Config->set_slave_source (src);
1111
1112         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1113         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1114                 if (!(*i)->hidden()) {
1115                         if ((*i)->realtime_set_speed ((*i)->speed(), true)) {
1116                                 non_rt_required = true;
1117                         }
1118                         (*i)->set_slaved (_slave);
1119                 }
1120         }
1121
1122         if (reverse) {
1123                 reverse_diskstream_buffers ();
1124         }
1125
1126         if (non_rt_required) {
1127                 post_transport_work = PostTransportWork (post_transport_work | PostTransportSpeed);
1128                 _butler->schedule_transport_work ();
1129         }
1130
1131         set_dirty();
1132 }
1133
1134 void
1135 Session::reverse_diskstream_buffers ()
1136 {
1137         post_transport_work = PostTransportWork (post_transport_work | PostTransportReverse);
1138         _butler->schedule_transport_work ();
1139 }
1140
1141 void
1142 Session::set_diskstream_speed (Diskstream* stream, double speed)
1143 {
1144         if (stream->realtime_set_speed (speed, false)) {
1145                 post_transport_work = PostTransportWork (post_transport_work | PostTransportSpeed);
1146                 _butler->schedule_transport_work ();
1147                 set_dirty ();
1148         }
1149 }
1150
1151 void
1152 Session::set_audio_range (list<AudioRange>& range)
1153 {
1154         Event *ev = new Event (Event::SetAudioRange, Event::Add, Event::Immediate, 0, 0.0f);
1155         ev->audio_range = range;
1156         queue_event (ev);
1157 }
1158
1159 void
1160 Session::request_play_range (bool yn)
1161 {
1162         Event* ev = new Event (Event::SetPlayRange, Event::Add, Event::Immediate, 0, 0.0f, yn);
1163         queue_event (ev);
1164 }
1165
1166 void
1167 Session::set_play_range (bool yn)
1168 {
1169         /* Called from event-processing context */
1170
1171         if (_play_range != yn) {
1172                 _play_range = yn;
1173                 setup_auto_play ();
1174
1175                 if (!_play_range) {
1176                         /* stop transport */
1177                         Event* ev = new Event (Event::SetTransportSpeed, Event::Add, Event::Immediate, 0, 0.0f, false);
1178                         merge_event (ev);
1179                 }
1180         }
1181 }
1182
1183 void
1184 Session::setup_auto_play ()
1185 {
1186         /* Called from event-processing context */
1187
1188         Event* ev;
1189
1190         _clear_event_type (Event::RangeStop);
1191         _clear_event_type (Event::RangeLocate);
1192
1193         if (!_play_range) {
1194                 return;
1195         }
1196
1197         list<AudioRange>::size_type sz = current_audio_range.size();
1198
1199         if (sz > 1) {
1200
1201                 list<AudioRange>::iterator i = current_audio_range.begin();
1202                 list<AudioRange>::iterator next;
1203
1204                 while (i != current_audio_range.end()) {
1205
1206                         next = i;
1207                         ++next;
1208
1209                         /* locating/stopping is subject to delays for declicking.
1210                          */
1211
1212                         nframes_t requested_frame = (*i).end;
1213
1214                         if (requested_frame > current_block_size) {
1215                                 requested_frame -= current_block_size;
1216                         } else {
1217                                 requested_frame = 0;
1218                         }
1219
1220                         if (next == current_audio_range.end()) {
1221                                 ev = new Event (Event::RangeStop, Event::Add, requested_frame, 0, 0.0f);
1222                         } else {
1223                                 ev = new Event (Event::RangeLocate, Event::Add, requested_frame, (*next).start, 0.0f);
1224                         }
1225
1226                         merge_event (ev);
1227
1228                         i = next;
1229                 }
1230
1231         } else if (sz == 1) {
1232
1233                 ev = new Event (Event::RangeStop, Event::Add, current_audio_range.front().end, 0, 0.0f);
1234                 merge_event (ev);
1235
1236         }
1237
1238         /* now start rolling at the right place */
1239
1240         ev = new Event (Event::LocateRoll, Event::Add, Event::Immediate, current_audio_range.front().start, 0.0f, false);
1241         merge_event (ev);
1242 }
1243
1244 void
1245 Session::request_roll_at_and_return (nframes_t start, nframes_t return_to)
1246 {
1247         Event *ev = new Event (Event::LocateRollLocate, Event::Add, Event::Immediate, return_to, 1.0);
1248         ev->target2_frame = start;
1249         queue_event (ev);
1250 }
1251
1252 void
1253 Session::request_bounded_roll (nframes_t start, nframes_t end)
1254 {
1255         request_stop ();
1256         Event *ev = new Event (Event::StopOnce, Event::Replace, end, Event::Immediate, 0.0);
1257         queue_event (ev);
1258         request_locate (start, true);
1259 }
1260
1261 void
1262 Session::engine_halted ()
1263 {
1264         bool ignored;
1265
1266         /* there will be no more calls to process(), so
1267            we'd better clean up for ourselves, right now.
1268
1269            but first, make sure the butler is out of
1270            the picture.
1271         */
1272
1273         g_atomic_int_set (&_butler->should_do_transport_work, 0);
1274         post_transport_work = PostTransportWork (0);
1275         _butler->stop ();
1276
1277         realtime_stop (false);
1278         non_realtime_stop (false, 0, ignored);
1279         transport_sub_state = 0;
1280
1281         TransportStateChange (); /* EMIT SIGNAL */
1282 }
1283
1284
1285 void
1286 Session::xrun_recovery ()
1287 {
1288         Xrun (transport_frame()); //EMIT SIGNAL
1289
1290         if (Config->get_stop_recording_on_xrun() && actively_recording()) {
1291
1292                 /* it didn't actually halt, but we need
1293                    to handle things in the same way.
1294                 */
1295
1296                 engine_halted();
1297         }
1298 }
1299
1300 void
1301 Session::update_latency_compensation (bool with_stop, bool abort)
1302 {
1303         bool update_jack = false;
1304
1305         if (_state_of_the_state & Deletion) {
1306                 return;
1307         }
1308
1309         _worst_track_latency = 0;
1310
1311 #undef DEBUG_LATENCY
1312 #ifdef DEBUG_LATENCY
1313         cerr << "\n---------------------------------\nUPDATE LATENCY\n";
1314 #endif
1315
1316         boost::shared_ptr<RouteList> r = routes.reader ();
1317
1318         for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1319
1320                 if (with_stop) {
1321                         (*i)->handle_transport_stopped (abort, (post_transport_work & PostTransportLocate),
1322                                                         (!(post_transport_work & PostTransportLocate) || pending_locate_flush));
1323                 }
1324
1325                 nframes_t old_latency = (*i)->output()->signal_latency ();
1326                 nframes_t track_latency = (*i)->update_total_latency ();
1327
1328                 if (old_latency != track_latency) {
1329                         (*i)->input()->update_port_total_latencies ();
1330                         (*i)->output()->update_port_total_latencies ();
1331                         update_jack = true;
1332                 }
1333
1334                 if (!(*i)->is_hidden() && ((*i)->active())) {
1335                         _worst_track_latency = max (_worst_track_latency, track_latency);
1336                 }
1337         }
1338
1339         if (update_jack) {
1340                 _engine.update_total_latencies ();
1341         }
1342
1343 #ifdef DEBUG_LATENCY
1344         cerr << "\tworst was " << _worst_track_latency << endl;
1345 #endif
1346
1347         for (RouteList::iterator i = r->begin(); i != r->end(); ++i) {
1348                 (*i)->set_latency_delay (_worst_track_latency);
1349         }
1350
1351         set_worst_io_latencies ();
1352
1353         /* reflect any changes in latencies into capture offsets
1354         */
1355
1356         boost::shared_ptr<DiskstreamList> dsl = diskstreams.reader();
1357
1358         for (DiskstreamList::iterator i = dsl->begin(); i != dsl->end(); ++i) {
1359                 (*i)->set_capture_offset ();
1360         }
1361 }
1362
1363 void
1364 Session::allow_auto_play (bool yn)
1365 {
1366         auto_play_legal = yn;
1367 }
1368
1369 void
1370 Session::reset_jack_connection (jack_client_t* jack)
1371 {
1372         JACK_Slave* js;
1373
1374         if (_slave && ((js = dynamic_cast<JACK_Slave*> (_slave)) != 0)) {
1375                 js->reset_client (jack);
1376         }
1377 }