Improved ExportProfileManager error handling, and added some missing (?) initialization
[ardour.git] / libs / ardour / audioengine.cc
1 /*
2     Copyright (C) 2002 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 <unistd.h>
21 #include <cerrno>
22 #include <vector>
23 #include <exception>
24 #include <stdexcept>
25 #include <sstream>
26
27 #include <glibmm/timer.h>
28 #include <pbd/pthread_utils.h>
29 #include <pbd/stacktrace.h>
30 #include <pbd/unknown_type.h>
31
32 #include <midi++/jack.h>
33
34 #include <ardour/audioengine.h>
35 #include <ardour/buffer.h>
36 #include <ardour/port.h>
37 #include <ardour/jack_audio_port.h>
38 #include <ardour/jack_midi_port.h>
39 #include <ardour/audio_port.h>
40 #include <ardour/session.h>
41 #include <ardour/cycle_timer.h>
42 #include <ardour/utils.h>
43 #ifdef VST_SUPPORT
44 #include <fst.h>
45 #endif
46
47 #include <ardour/timestamps.h>
48
49 #include "i18n.h"
50
51 using namespace std;
52 using namespace ARDOUR;
53 using namespace PBD;
54
55 gint AudioEngine::m_meter_exit;
56
57 static void 
58 ardour_jack_error (const char* msg) 
59 {
60         error << "JACK: " << msg << endmsg;
61 }
62
63 AudioEngine::AudioEngine (string client_name) 
64         : ports (new Ports)
65 {
66         session = 0;
67         session_remove_pending = false;
68         _running = false;
69         _has_run = false;
70         last_monitor_check = 0;
71         monitor_check_interval = max_frames;
72         _processed_frames = 0;
73         _usecs_per_cycle = 0;
74         _jack = 0;
75         _frame_rate = 0;
76         _buffer_size = 0;
77         _freewheel_thread_registered = false;
78         _freewheeling = false;
79
80         m_meter_thread = 0;
81         g_atomic_int_set (&m_meter_exit, 0);
82
83         if (connect_to_jack (client_name)) {
84                 throw NoBackendAvailable ();
85         }
86
87         Port::set_engine (this);
88         
89         Parameter::init_metadata(NullAutomation);
90         Parameter::init_metadata(GainAutomation);
91         Parameter::init_metadata(PanAutomation);
92         Parameter::init_metadata(PluginAutomation);
93         Parameter::init_metadata(SoloAutomation);
94         Parameter::init_metadata(MuteAutomation);
95         Parameter::init_metadata(MidiCCAutomation);
96         Parameter::init_metadata(MidiPgmChangeAutomation);
97         Parameter::init_metadata(MidiPitchBenderAutomation);
98         Parameter::init_metadata(MidiChannelPressureAutomation);
99         Parameter::init_metadata(FadeInAutomation);
100         Parameter::init_metadata(FadeOutAutomation);
101         Parameter::init_metadata(EnvelopeAutomation);
102         Parameter::init_metadata(MidiCCAutomation);
103 }
104
105 AudioEngine::~AudioEngine ()
106 {
107         {
108                 Glib::Mutex::Lock tm (_process_lock);
109                 session_removed.signal ();
110                 
111                 if (_running) {
112                         jack_client_close (_jack);
113                         _jack = 0;
114                 }
115                 
116                 stop_metering_thread ();
117         }
118 }
119
120 jack_client_t*
121 AudioEngine::jack() const
122 {
123         return _jack;
124 }
125
126 void
127 _thread_init_callback (void *arg)
128 {
129         /* make sure that anybody who needs to know about this thread
130            knows about it.
131         */
132
133         PBD::ThreadCreatedWithRequestSize (pthread_self(), X_("Audioengine"), 4096);
134         MIDI::JACK_MidiPort::set_process_thread (pthread_self());
135 }
136
137 int
138 AudioEngine::start ()
139 {
140         if (!_jack) {
141                 error << _("AudioEngine::start() called while disconnected from JACK") << endmsg;
142                 return -1;
143         }
144
145         if (!_running) {
146
147                 if (session) {
148                         nframes_t blocksize = jack_get_buffer_size (_jack);
149
150                         BootMessage (_("Connect session to engine"));
151
152                         session->set_block_size (blocksize);
153                         session->set_frame_rate (jack_get_sample_rate (_jack));
154
155                         /* page in as much of the session process code as we
156                            can before we really start running.
157                         */
158
159                         session->process (blocksize);
160                         session->process (blocksize);
161                         session->process (blocksize);
162                         session->process (blocksize);
163                         session->process (blocksize);
164                         session->process (blocksize);
165                         session->process (blocksize);
166                         session->process (blocksize);
167                 }
168
169                 _processed_frames = 0;
170                 last_monitor_check = 0;
171
172                 jack_on_shutdown (_jack, halted, this);
173                 jack_set_graph_order_callback (_jack, _graph_order_callback, this);
174                 jack_set_thread_init_callback (_jack, _thread_init_callback, this);
175                 jack_set_process_callback (_jack, _process_callback, this);
176                 jack_set_sample_rate_callback (_jack, _sample_rate_callback, this);
177                 jack_set_buffer_size_callback (_jack, _bufsize_callback, this);
178                 jack_set_xrun_callback (_jack, _xrun_callback, this);
179                 jack_set_sync_callback (_jack, _jack_sync_callback, this);
180                 jack_set_freewheel_callback (_jack, _freewheel_callback, this);
181
182                 if (Config->get_jack_time_master()) {
183                         jack_set_timebase_callback (_jack, 0, _jack_timebase_callback, this);
184                 }
185
186                 if (jack_activate (_jack) == 0) {
187                         _running = true;
188                         _has_run = true;
189                         Running(); /* EMIT SIGNAL */
190                 } else {
191                         // error << _("cannot activate JACK client") << endmsg;
192                 }
193
194                 start_metering_thread();
195         }
196
197         return _running ? 0 : -1;
198 }
199
200 int
201 AudioEngine::stop (bool forever)
202 {
203         if (_jack) {
204                 if (forever) {
205                         disconnect_from_jack ();
206                 } else {
207                         jack_deactivate (_jack);
208                         Stopped(); /* EMIT SIGNAL */
209                 }
210         }
211
212         return _running ? -1 : 0;
213 }
214
215
216 bool
217 AudioEngine::get_sync_offset (nframes_t& offset) const
218 {
219
220 #ifdef HAVE_JACK_VIDEO_SUPPORT
221
222         jack_position_t pos;
223         
224         if (_jack) {
225                 (void) jack_transport_query (_jack, &pos);
226                 
227                 if (pos.valid & JackVideoFrameOffset) {
228                         offset = pos.video_offset;
229                         return true;
230                 }
231         }
232
233 #endif
234
235         return false;
236 }
237
238 void
239 AudioEngine::_jack_timebase_callback (jack_transport_state_t state, nframes_t nframes,
240                                       jack_position_t* pos, int new_position, void *arg)
241 {
242         static_cast<AudioEngine*> (arg)->jack_timebase_callback (state, nframes, pos, new_position);
243 }
244
245 void
246 AudioEngine::jack_timebase_callback (jack_transport_state_t state, nframes_t nframes,
247                                      jack_position_t* pos, int new_position)
248 {
249         if (_jack && session && session->synced_to_jack()) {
250                 session->jack_timebase_callback (state, nframes, pos, new_position);
251         }
252 }
253
254 int
255 AudioEngine::_jack_sync_callback (jack_transport_state_t state, jack_position_t* pos, void* arg)
256 {
257         return static_cast<AudioEngine*> (arg)->jack_sync_callback (state, pos);
258 }
259
260 int
261 AudioEngine::jack_sync_callback (jack_transport_state_t state, jack_position_t* pos)
262 {
263         if (_jack && session) {
264                 return session->jack_sync_callback (state, pos);
265         }
266
267         return true;
268 }
269
270 int
271 AudioEngine::_xrun_callback (void *arg)
272 {
273         AudioEngine* ae = static_cast<AudioEngine*> (arg);
274         if (ae->connected()) {
275                 ae->Xrun (); /* EMIT SIGNAL */
276         }
277         return 0;
278 }
279
280 int
281 AudioEngine::_graph_order_callback (void *arg)
282 {
283         AudioEngine* ae = static_cast<AudioEngine*> (arg);
284         if (ae->connected()) {
285                 ae->GraphReordered (); /* EMIT SIGNAL */
286         }
287         return 0;
288 }
289
290 /** Wrapped which is called by JACK as its process callback.  It is just
291  * here to get us back into C++ land by calling AudioEngine::process_callback()
292  * @param nframes Number of frames passed by JACK.
293  * @param arg User argument passed by JACK, which will be the AudioEngine*.
294  */
295 int
296 AudioEngine::_process_callback (nframes_t nframes, void *arg)
297 {
298         return static_cast<AudioEngine *> (arg)->process_callback (nframes);
299 }
300
301 void
302 AudioEngine::_freewheel_callback (int onoff, void *arg)
303 {
304         static_cast<AudioEngine*>(arg)->_freewheeling = onoff;
305 }
306
307 /** Method called by JACK (via _process_callback) which says that there
308  * is work to be done.
309  * @param nframes Number of frames to process.
310  */
311 int
312 AudioEngine::process_callback (nframes_t nframes)
313 {
314         // CycleTimer ct ("AudioEngine::process");
315         Glib::Mutex::Lock tm (_process_lock, Glib::TRY_LOCK);
316
317         /// The number of frames that will have been processed when we've finished
318         nframes_t next_processed_frames;
319         
320         /* handle wrap around of total frames counter */
321
322         if (max_frames - _processed_frames < nframes) {
323                 next_processed_frames = nframes - (max_frames - _processed_frames);
324         } else {
325                 next_processed_frames = _processed_frames + nframes;
326         }
327
328         if (!tm.locked() || session == 0) {
329                 /* return having done nothing */
330                 _processed_frames = next_processed_frames;
331                 return 0;
332         }
333
334         if (session_remove_pending) {
335                 /* perform the actual session removal */
336                 session = 0;
337                 session_remove_pending = false;
338                 session_removed.signal();
339                 _processed_frames = next_processed_frames;
340                 return 0;
341         }
342
343         boost::shared_ptr<Ports> p = ports.reader();
344
345         // Prepare ports (ie read data if necessary)
346         for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
347                 (*i)->cycle_start (nframes, 0);
348         }
349
350         if (_freewheeling) {
351                 /* emit the Freewheel signal and stop freewheeling in the event of trouble */
352                 if (Freewheel (nframes)) {
353                         jack_set_freewheel (_jack, false);
354                 }
355
356         } else {
357                 if (session) {
358                         session->process (nframes);
359                 }
360         }
361         
362         // Finalize ports (ie write data if necessary)
363
364         for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
365                 (*i)->cycle_end (nframes, 0);
366         }
367
368         if (_freewheeling) {
369                 return 0;
370         }
371
372         if (!_running) {
373                 _processed_frames = next_processed_frames;
374                 return 0;
375         }
376
377         if (last_monitor_check + monitor_check_interval < next_processed_frames) {
378
379                 boost::shared_ptr<Ports> p = ports.reader();
380
381                 for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
382                         
383                         Port *port = (*i);
384                         bool x;
385                         
386                         if (port->_last_monitor != (x = port->monitoring_input ())) {
387                                 port->_last_monitor = x;
388                                 /* XXX I think this is dangerous, due to 
389                                    a likely mutex in the signal handlers ...
390                                 */
391                                  port->MonitorInputChanged (x); /* EMIT SIGNAL */
392                         }
393                 }
394                 last_monitor_check = next_processed_frames;
395         }
396
397         if (session->silent()) {
398
399                 boost::shared_ptr<Ports> p = ports.reader();
400
401                 for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
402                         
403                         Port *port = (*i);
404                         
405                         if (port->sends_output()) {
406                                 port->get_buffer().silence(nframes);
407                         }
408                 }
409         }
410
411         _processed_frames = next_processed_frames;
412         return 0;
413 }
414
415 int
416 AudioEngine::_sample_rate_callback (nframes_t nframes, void *arg)
417 {
418         return static_cast<AudioEngine *> (arg)->jack_sample_rate_callback (nframes);
419 }
420
421 int
422 AudioEngine::jack_sample_rate_callback (nframes_t nframes)
423 {
424         _frame_rate = nframes;
425         _usecs_per_cycle = (int) floor ((((double) frames_per_cycle() / nframes)) * 1000000.0);
426         
427         /* check for monitor input change every 1/10th of second */
428
429         monitor_check_interval = nframes / 10;
430         last_monitor_check = 0;
431         
432         if (session) {
433                 session->set_frame_rate (nframes);
434         }
435
436         SampleRateChanged (nframes); /* EMIT SIGNAL */
437
438         return 0;
439 }
440
441 int
442 AudioEngine::_bufsize_callback (nframes_t nframes, void *arg)
443 {
444         return static_cast<AudioEngine *> (arg)->jack_bufsize_callback (nframes);
445 }
446
447 int
448 AudioEngine::jack_bufsize_callback (nframes_t nframes)
449 {
450         _buffer_size = nframes;
451         _usecs_per_cycle = (int) floor ((((double) nframes / frame_rate())) * 1000000.0);
452         last_monitor_check = 0;
453
454         boost::shared_ptr<Ports> p = ports.reader();
455
456         for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
457                 (*i)->reset();
458         }
459
460         if (session) {
461                 session->set_block_size (_buffer_size);
462         }
463
464         return 0;
465 }
466
467 void
468 AudioEngine::stop_metering_thread ()
469 {
470         if (m_meter_thread) {
471                 g_atomic_int_set (&m_meter_exit, 1);
472                 m_meter_thread->join ();
473                 m_meter_thread = 0;
474         }
475 }
476
477 void
478 AudioEngine::start_metering_thread ()
479 {
480         if (m_meter_thread == 0) {
481                 g_atomic_int_set (&m_meter_exit, 0);
482                 m_meter_thread = Glib::Thread::create (sigc::mem_fun(this, &AudioEngine::meter_thread),
483                                                        500000, true, true, Glib::THREAD_PRIORITY_NORMAL);
484         }
485 }
486
487 void
488 AudioEngine::meter_thread ()
489 {
490         while (true) {
491                 Glib::usleep (10000); /* 1/100th sec interval */
492                 if (g_atomic_int_get(&m_meter_exit)) {
493                         break;
494                 }
495                 IO::update_meters ();
496         }
497 }
498
499 void 
500 AudioEngine::set_session (Session *s)
501 {
502         Glib::Mutex::Lock pl (_process_lock);
503
504         if (!session) {
505
506                 session = s;
507
508                 nframes_t blocksize = jack_get_buffer_size (_jack);
509                 
510                 /* page in as much of the session process code as we
511                    can before we really start running.
512                 */
513                 
514                 boost::shared_ptr<Ports> p = ports.reader();
515
516                 for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
517                         (*i)->cycle_start (blocksize, 0);
518                 }
519
520                 s->process (blocksize);
521                 s->process (blocksize);
522                 s->process (blocksize);
523                 s->process (blocksize);
524                 s->process (blocksize);
525                 s->process (blocksize);
526                 s->process (blocksize);
527                 s->process (blocksize);
528
529                 for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
530                         (*i)->cycle_end (blocksize, 0);
531                 }
532         }
533 }
534
535 void 
536 AudioEngine::remove_session ()
537 {
538         Glib::Mutex::Lock lm (_process_lock);
539
540         if (_running) {
541
542                 if (session) {
543                         session_remove_pending = true;
544                         session_removed.wait(_process_lock);
545                 }
546
547         } else {
548                 session = 0;
549         }
550         
551         //FIXME: Preliminary bugfix for  http://tracker.ardour.org/view.php?id=1985
552         //remove_all_ports ();
553 }
554
555 void
556 AudioEngine::port_registration_failure (const std::string& portname)
557 {
558         string full_portname = jack_client_name;
559         full_portname += ':';
560         full_portname += portname;
561         
562         
563         jack_port_t* p = jack_port_by_name (_jack, full_portname.c_str());
564         string reason;
565         
566         if (p) {
567                 reason = _("a port with this name already exists: check for duplicated track/bus names");
568         } else {
569                 reason = _("unknown error");
570         }
571         
572         throw PortRegistrationFailure (string_compose (_("AudioEngine: cannot register port \"%1\": %2"), portname, reason).c_str());
573 }       
574
575 Port *
576 AudioEngine::register_port (DataType dtype, const string& portname, bool input, bool publish)
577 {
578         Port* newport = 0;
579
580         /*cerr << "trying to register port with name " << portname << endl;*/
581         try {
582                 if (dtype == DataType::AUDIO) {
583                         newport = new AudioPort (portname, (input ? Port::IsInput : Port::IsOutput), publish, frames_per_cycle());
584                 } else if (dtype == DataType::MIDI) {
585                         newport = new MidiPort (portname, (input ? Port::IsInput : Port::IsOutput), publish, frames_per_cycle());
586                 } else {
587                         throw unknown_type();
588                 }
589
590                 /*cerr << "successfully got port " << portname << " with address " << newport << endl;*/
591
592                 RCUWriter<Ports> writer (ports);
593                 boost::shared_ptr<Ports> ps = writer.get_copy ();
594                 /*cerr << "Address of ports list: " << ps << endl
595                      << "Ports set size before insert: " << ps->size() << endl;*/
596                 ps->insert (ps->begin(), newport);
597                 /*cerr << "Ports set size after insert: " << ps->size() << endl;*/
598
599                 /* writer goes out of scope, forces update */
600
601                 return newport;
602         }
603
604         catch (...) {
605                 throw PortRegistrationFailure("unable to create port (unknown type?)");
606         }
607 }
608
609 Port*
610 AudioEngine::get_port (const std::string& full_name)
611 {
612         boost::shared_ptr<Ports> p = ports.reader();
613         
614         for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
615                 //cerr << "comparing port name '" << (*i)->name() << "' with '" << full_name << "'" << endl;
616                 if ((*i)->name() == full_name) {
617                         return *i;
618                 }
619         }
620         return 0;
621 }
622
623
624 Port *
625 AudioEngine::register_input_port (DataType type, const string& portname, bool publish)
626 {
627         return register_port (type, portname, true, publish);
628 }
629
630 Port *
631 AudioEngine::register_output_port (DataType type, const string& portname, bool publish)
632 {
633         return register_port (type, portname, false, publish);
634 }
635
636 int
637 AudioEngine::unregister_port (Port& port)
638 {
639         /* caller must hold process lock */
640
641         cerr << "about to unregister Port xx  x" << &port << "\n";
642
643         if (!_running) { 
644                 /* probably happening when the engine has been halted by JACK,
645                    in which case, there is nothing we can do here.
646                    */
647                 cerr << "not running\n";
648                 return 0;
649         }
650
651         {
652                 cerr << "before getcopy\n";
653                 
654                 RCUWriter<Ports> writer (ports);
655                 boost::shared_ptr<Ports> ps = writer.get_copy ();
656                 
657                 cerr << "Ports set size: " << ps.get()->size() << endl;
658
659                 for (Ports::iterator i = ps->begin(); i != ps->end(); ++i) {
660                         cerr << "before delete" << endl;
661                         if ((*i) == &port) {
662                                 cerr << "About to delete " << &port << endl;
663                                 delete *i;
664                                 ps->erase (i);
665                                 cerr << "After erasing ports size: " << ps->size();
666                                 break;
667                         }
668                 }
669                 
670                 /* writer goes out of scope, forces update */
671         }
672                 
673         cerr << "before remove_connections\n";
674         remove_connections_for (port);
675
676         return 0;
677 }
678
679 int 
680 AudioEngine::connect (const string& source, const string& destination)
681 {
682         int ret;
683
684         if (!_running) {
685                 if (!_has_run) {
686                         fatal << _("connect called before engine was started") << endmsg;
687                         /*NOTREACHED*/
688                 } else {
689                         return -1;
690                 }
691         }
692
693         string s = make_port_name_non_relative (source);
694         string d = make_port_name_non_relative (destination);
695                 
696         //cerr << "Trying to connect source: " << s << " with destination " << d << endl;
697         
698         Port* src = get_port (s);
699         Port* dst = get_port (d);
700
701         if (src && dst) {
702
703                 /* both ports are known to us, so do the internal connect stuff */
704
705                 if ((ret = src->connect (*dst)) == 0) {
706                         ret = dst->connect (*src);
707                 }
708
709         } else if (src || dst) {
710
711                 /* one port is known to us, try to connect it to something external */
712
713                 PortConnectableByName* pcn;
714                 string other;
715
716                 if (src) {
717                         pcn = dynamic_cast<PortConnectableByName*>(src);
718                         other = d;
719                 } else {
720                         pcn = dynamic_cast<PortConnectableByName*>(dst);
721                         other = s;
722                 }
723
724                 if (pcn) {
725                         ret = pcn->connect (other);
726                 } else {
727                         ret = -1;
728                 }
729
730         } else {
731
732                 /* neither port is known to us, and this API isn't intended for use as a general patch bay */
733
734                 ret = -1;
735                 
736         }
737         
738         if (ret > 0) {
739                 error << string_compose(_("AudioEngine: connection already exists: %1 (%2) to %3 (%4)"), 
740                                         source, s, destination, d) 
741                       << endmsg;
742         } else if (ret < 0) {
743                 error << string_compose(_("AudioEngine: cannot connect %1 (%2) to %3 (%4)"), 
744                                         source, s, destination, d) 
745                       << endmsg;
746         }
747
748         return ret;
749 }
750
751 int 
752 AudioEngine::disconnect (const string& source, const string& destination)
753 {
754         int ret;
755
756         if (!_running) {
757                 if (!_has_run) {
758                         fatal << _("disconnect called before engine was started") << endmsg;
759                         /*NOTREACHED*/
760                 } else {
761                         return -1;
762                 }
763         }
764         
765         string s = make_port_name_non_relative (source);
766         string d = make_port_name_non_relative (destination);
767
768         //cerr << "trying to disconnect port '" << s << "' from port '" << d << endl;
769         
770         Port* src = get_port (s);
771         Port* dst = get_port (d);
772
773         if (src && dst) {
774
775                 /* both ports are known to us, so do the internal connect stuff */
776                 
777                 if ((ret = src->disconnect (*dst)) == 0) {
778                         ret = dst->disconnect (*src);
779                 }
780
781         } else if (src || dst) {
782
783                 /* one port is known to us, try to connect it to something external */
784
785
786                 PortConnectableByName* pcn;
787                 string other;
788
789                 if (src) {
790                         pcn = dynamic_cast<PortConnectableByName*>(src);
791                         other = d;
792                 } else {
793                         pcn = dynamic_cast<PortConnectableByName*>(dst);
794                         other = s;
795                 }
796
797                 if (pcn) {
798                         ret = pcn->disconnect (other);
799                 } else {
800                         ret = -1;
801                 }
802
803         } else {
804
805                 /* neither port is known to us, and this API isn't intended for use as a general patch bay */
806                 
807                 ret = -1;
808                 
809         }
810         
811         return ret;
812 }
813
814 int
815 AudioEngine::disconnect (Port& port)
816 {
817         if (!_running) {
818                 if (!_has_run) {
819                         fatal << _("disconnect called before engine was started") << endmsg;
820                         /*NOTREACHED*/
821                 } else {
822                         return -1;
823                 }
824         }
825
826         return port.disconnect_all ();
827 }
828
829 ARDOUR::nframes_t
830 AudioEngine::frame_rate ()
831 {
832         if (_jack) {
833                 if (_frame_rate == 0) {
834                         return (_frame_rate = jack_get_sample_rate (_jack));
835                 } else {
836                         return _frame_rate;
837                 }
838         } else {
839                 fatal << X_("programming error: AudioEngine::frame_rate() called while disconnected from JACK")
840                       << endmsg;
841                 /*NOTREACHED*/
842                 return 0;
843         }
844 }
845
846 ARDOUR::nframes_t
847 AudioEngine::frames_per_cycle ()
848 {
849         if (_jack) {
850                 if (_buffer_size == 0) {
851                         return (_buffer_size = jack_get_buffer_size (_jack));
852                 } else {
853                         return _buffer_size;
854                 }
855         } else {
856                 fatal << X_("programming error: AudioEngine::frame_rate() called while disconnected from JACK")
857                       << endmsg;
858                 /*NOTREACHED*/
859                 return 0;
860         }
861 }
862
863 /** Get a port by name.
864  * Note this can return NULL, it will NOT create a port if it is not found (any more).
865  */
866 Port *
867 AudioEngine::get_port_by_name (const string& portname, bool keep)
868 {
869         Glib::Mutex::Lock lm (_process_lock);
870
871         if (!_running) {
872                 if (!_has_run) {
873                         fatal << _("get_port_by_name() called before engine was started") << endmsg;
874                         /*NOTREACHED*/
875                 } else {
876                         return 0;
877                 }
878         }
879         
880         boost::shared_ptr<Ports> pr = ports.reader();
881         
882         for (Ports::iterator i = pr->begin(); i != pr->end(); ++i) {
883                 if (portname == (*i)->name()) {
884                         return (*i);
885                 }
886         }
887
888         return 0;
889 }
890
891 const char **
892 AudioEngine::get_ports (const string& port_name_pattern, const string& type_name_pattern, uint32_t flags)
893 {
894         if (!_running) {
895                 if (!_has_run) {
896                         fatal << _("get_ports called before engine was started") << endmsg;
897                         /*NOTREACHED*/
898                 } else {
899                         return 0;
900                 }
901         }
902         return jack_get_ports (_jack, port_name_pattern.c_str(), type_name_pattern.c_str(), flags);
903 }
904
905 void
906 AudioEngine::halted (void *arg)
907 {
908         AudioEngine* ae = static_cast<AudioEngine *> (arg);
909         bool was_running = ae->_running;
910
911         ae->stop_metering_thread ();
912
913         ae->_running = false;
914         ae->_buffer_size = 0;
915         ae->_frame_rate = 0;
916
917         cerr << "!!! HALTED !!!\n";
918
919         if (was_running) {
920                 ae->Halted(); /* EMIT SIGNAL */
921         }
922 }
923
924 bool
925 AudioEngine::can_request_hardware_monitoring () 
926 {
927         const char ** ports;
928
929         if (!_jack) {
930                 return 0;
931         }
932
933         if ((ports = jack_get_ports (_jack, NULL, JACK_DEFAULT_AUDIO_TYPE, JackPortCanMonitor)) == 0) {
934                 return false;
935         }
936
937         free (ports);
938
939         return true;
940 }
941
942
943 uint32_t
944 AudioEngine::n_physical_outputs (DataType type) const
945 {
946         const char ** ports;
947         uint32_t i = 0;
948
949         if (!_jack) {
950                 return 0;
951         }
952
953         if ((ports = jack_get_ports (_jack, NULL, type.to_jack_type(), JackPortIsPhysical|JackPortIsInput)) == 0) {
954                 return 0;
955         }
956
957         for (i = 0; ports[i]; ++i);
958         free (ports);
959
960         return i;
961 }
962
963 uint32_t
964 AudioEngine::n_physical_inputs (DataType type) const
965 {
966         const char ** ports;
967         uint32_t i = 0;
968         
969         if (!_jack) {
970                 return 0;
971         }
972         
973         if ((ports = jack_get_ports (_jack, NULL, type.to_jack_type(), JackPortIsPhysical|JackPortIsOutput)) == 0) {
974                 return 0;
975         }
976
977         if (ports) {
978                 for (i = 0; ports[i]; ++i);
979                 free (ports);
980         }
981         return i;
982 }
983
984 void
985 AudioEngine::get_physical_inputs (DataType type, vector<string>& ins)
986 {
987         const char ** ports;
988         uint32_t i = 0;
989         
990         if (!_jack) {
991                 return;
992         }
993         
994         if ((ports = jack_get_ports (_jack, NULL, type.to_jack_type(), JackPortIsPhysical|JackPortIsOutput)) == 0) {
995                 return;
996         }
997
998         if (ports) {
999                 for (i = 0; ports[i]; ++i) {
1000                         ins.push_back (ports[i]);
1001                 }
1002                 free (ports);
1003         }
1004 }
1005
1006 void
1007 AudioEngine::get_physical_outputs (DataType type, vector<string>& outs)
1008 {
1009         const char ** ports;
1010         uint32_t i = 0;
1011         
1012         if (!_jack) {
1013                 return;
1014         }
1015         
1016         if ((ports = jack_get_ports (_jack, NULL, type.to_jack_type(), JackPortIsPhysical|JackPortIsInput)) == 0) {
1017                 return;
1018         }
1019
1020         if (ports) {
1021                 for (i = 0; ports[i]; ++i) {
1022                         outs.push_back (ports[i]);
1023                 }
1024                 free (ports);
1025         }
1026 }
1027
1028 string
1029 AudioEngine::get_nth_physical (DataType type, uint32_t n, int flag)
1030 {
1031         const char ** ports;
1032         uint32_t i;
1033         string ret;
1034
1035         assert(type != DataType::NIL);
1036
1037         if (!_running || !_jack) {
1038                 if (!_has_run) {
1039                         fatal << _("get_nth_physical called before engine was started") << endmsg;
1040                         /*NOTREACHED*/
1041                 } else {
1042                         return "";
1043                 }
1044         }
1045
1046         ports = jack_get_ports (_jack, NULL, type.to_jack_type(), JackPortIsPhysical|flag);
1047         
1048         if (ports == 0) {
1049                 return "";
1050         }
1051
1052         for (i = 0; i < n && ports[i]; ++i);
1053
1054         if (ports[i]) {
1055                 ret = ports[i];
1056         }
1057
1058         free ((char *) ports);
1059
1060         return ret;
1061 }
1062
1063 ARDOUR::nframes_t
1064 AudioEngine::get_port_total_latency (const Port& port)
1065 {
1066         return port.total_latency ();
1067 }
1068
1069 void
1070 AudioEngine::update_total_latency (const Port& port)
1071 {
1072         if (!_jack) {
1073                 fatal << _("update_total_latency() called with no JACK client connection") << endmsg;
1074                 /*NOTREACHED*/
1075         }
1076
1077         if (!_running) {
1078                 if (!_has_run) {
1079                         fatal << _("update_total_latency() called before engine was started") << endmsg;
1080                         /*NOTREACHED*/
1081                 } 
1082         }
1083
1084         port.recompute_total_latency ();
1085 }
1086
1087 void
1088 AudioEngine::transport_stop ()
1089 {
1090         if (_jack) {
1091                 jack_transport_stop (_jack);
1092         }
1093 }
1094
1095 void
1096 AudioEngine::transport_start ()
1097 {
1098         // cerr << "tell JACK to start\n";
1099         if (_jack) {
1100                 jack_transport_start (_jack);
1101         }
1102 }
1103
1104 void
1105 AudioEngine::transport_locate (nframes_t where)
1106 {
1107         // cerr << "tell JACK to locate to " << where << endl;
1108         if (_jack) {
1109                 jack_transport_locate (_jack, where);
1110         }
1111 }
1112
1113 AudioEngine::TransportState
1114 AudioEngine::transport_state ()
1115 {
1116         if (_jack) {
1117                 jack_position_t pos;
1118                 return (TransportState) jack_transport_query (_jack, &pos);
1119         } else {
1120                 return (TransportState) JackTransportStopped;
1121         }
1122 }
1123
1124 int
1125 AudioEngine::reset_timebase ()
1126 {
1127         if (_jack) {
1128                 if (Config->get_jack_time_master()) {
1129                         return jack_set_timebase_callback (_jack, 0, _jack_timebase_callback, this);
1130                 } else {
1131                         return jack_release_timebase (_jack);
1132                 }
1133         } else {
1134                 return -1;
1135         }
1136 }
1137
1138 int
1139 AudioEngine::freewheel (bool onoff)
1140 {
1141         if (_jack) {
1142
1143                 if (onoff != _freewheeling) {
1144
1145                         if (onoff) {
1146                                 _freewheel_thread_registered = false;
1147                         }
1148
1149                         return jack_set_freewheel (_jack, onoff);
1150
1151                 } else {
1152                         /* already doing what has been asked for */
1153                         return 0;
1154                 }
1155
1156         } else {
1157                 return -1;
1158         }
1159 }
1160
1161 void
1162 AudioEngine::remove_all_ports ()
1163 {
1164         /* process lock MUST be held */
1165
1166         {
1167                 RCUWriter<Ports> writer (ports);
1168                 boost::shared_ptr<Ports> ps = writer.get_copy ();
1169                 ps->clear ();
1170         }
1171 }
1172
1173 void
1174 AudioEngine::remove_connections_for (Port& port)
1175 {
1176         for (PortConnections::iterator i = port_connections.begin(); i != port_connections.end(); ) {
1177                 PortConnections::iterator tmp;
1178                 
1179                 tmp = i;
1180                 ++tmp;
1181                 
1182                 if ((*i).first == port.name()) {
1183                         port_connections.erase (i);
1184                 }
1185
1186                 i = tmp;
1187         }
1188 }
1189
1190
1191 #ifdef HAVE_JACK_CLIENT_OPEN
1192
1193 int
1194 AudioEngine::connect_to_jack (string client_name)
1195 {
1196         jack_options_t options = JackNullOption;
1197         jack_status_t status;
1198         const char *server_name = NULL;
1199
1200         jack_client_name = client_name; /* might be reset below */
1201         _jack = jack_client_open (jack_client_name.c_str(), options, &status, server_name);
1202
1203         if (_jack == NULL) {
1204
1205                 if (status & JackServerFailed) {
1206                         error << _("Unable to connect to JACK server") << endmsg;
1207                 }
1208                 
1209                 // error message is not useful here
1210                 return -1;
1211         }
1212
1213         if (status & JackServerStarted) {
1214                 info << _("JACK server started") << endmsg;
1215         }
1216
1217         if (status & JackNameNotUnique) {
1218                 jack_client_name = jack_get_client_name (_jack);
1219         }
1220
1221         jack_set_error_function (ardour_jack_error);
1222         
1223         return 0;
1224 }
1225
1226 #else
1227
1228 int
1229 AudioEngine::connect_to_jack (string client_name)
1230 {
1231         jack_client_name = client_name;
1232
1233         if ((_jack = jack_client_new (client_name.c_str())) == 0) {
1234                 return -1;
1235         }
1236
1237         return 0;
1238 }
1239
1240 #endif /* HAVE_JACK_CLIENT_OPEN */
1241
1242 int 
1243 AudioEngine::disconnect_from_jack ()
1244 {
1245         if (!_jack) {
1246                 return 0;
1247         }
1248
1249
1250         if (_running) {
1251                 stop_metering_thread ();
1252         }
1253
1254         { 
1255                 Glib::Mutex::Lock lm (_process_lock);
1256                 jack_client_close (_jack);
1257                 _jack = 0;
1258         }
1259
1260         _buffer_size = 0;
1261         _frame_rate = 0;
1262
1263         if (_running) {
1264                 _running = false;
1265                 Stopped(); /* EMIT SIGNAL */
1266         }
1267
1268         return 0;
1269 }
1270
1271 int
1272 AudioEngine::reconnect_to_jack ()
1273 {
1274         if (_running) {
1275                 disconnect_from_jack ();
1276                 /* XXX give jackd a chance */
1277                 Glib::usleep (250000);
1278         }
1279
1280         if (connect_to_jack (jack_client_name)) {
1281                 error << _("failed to connect to JACK") << endmsg;
1282                 return -1;
1283         }
1284
1285         Ports::iterator i;
1286
1287         boost::shared_ptr<Ports> p = ports.reader ();
1288
1289         for (i = p->begin(); i != p->end(); ++i) {
1290                 if ((*i)->reestablish ()) {
1291                         break;
1292                 } 
1293         }
1294
1295         if (i != p->end()) {
1296                 /* failed */
1297                 remove_all_ports ();
1298                 return -1;
1299         } 
1300
1301
1302         if (session) {
1303                 session->reset_jack_connection (_jack);
1304                 nframes_t blocksize = jack_get_buffer_size (_jack);
1305                 session->set_block_size (blocksize);
1306                 session->set_frame_rate (jack_get_sample_rate (_jack));
1307         }
1308
1309         last_monitor_check = 0;
1310         
1311         jack_on_shutdown (_jack, halted, this);
1312         jack_set_graph_order_callback (_jack, _graph_order_callback, this);
1313         jack_set_thread_init_callback (_jack, _thread_init_callback, this);
1314         jack_set_process_callback (_jack, _process_callback, this);
1315         jack_set_sample_rate_callback (_jack, _sample_rate_callback, this);
1316         jack_set_buffer_size_callback (_jack, _bufsize_callback, this);
1317         jack_set_xrun_callback (_jack, _xrun_callback, this);
1318         jack_set_sync_callback (_jack, _jack_sync_callback, this);
1319         jack_set_freewheel_callback (_jack, _freewheel_callback, this);
1320         
1321         if (Config->get_jack_time_master()) {
1322                 jack_set_timebase_callback (_jack, 0, _jack_timebase_callback, this);
1323         }
1324         
1325         if (jack_activate (_jack) == 0) {
1326                 _running = true;
1327                 _has_run = true;
1328         } else {
1329                 return -1;
1330         }
1331
1332         /* re-establish connections */
1333         
1334         for (i = p->begin(); i != p->end(); ++i) {
1335                 (*i)->reconnect ();
1336         }
1337
1338         Running (); /* EMIT SIGNAL*/
1339
1340         start_metering_thread ();
1341
1342         return 0;
1343 }
1344
1345 int
1346 AudioEngine::request_buffer_size (nframes_t nframes)
1347 {
1348         if (_jack) {
1349
1350                 if (nframes == jack_get_buffer_size (_jack)) {
1351                         return 0;
1352                 }
1353
1354                 return jack_set_buffer_size (_jack, nframes);
1355
1356         } else {
1357                 return -1;
1358         }
1359 }
1360
1361 void
1362 AudioEngine::update_total_latencies ()
1363 {
1364 #ifdef HAVE_JACK_RECOMPUTE_LATENCIES
1365         if (_jack) {
1366                 jack_recompute_total_latencies (_jack);
1367         }
1368 #endif
1369 }
1370                 
1371 string
1372 AudioEngine::make_port_name_relative (string portname)
1373 {
1374         string::size_type len;
1375         string::size_type n;
1376         
1377         len = portname.length();
1378
1379         for (n = 0; n < len; ++n) {
1380                 if (portname[n] == ':') {
1381                         break;
1382                 }
1383         }
1384         
1385         if ((n != len) && (portname.substr (0, n) == jack_client_name)) {
1386                 return portname.substr (n+1);
1387         }
1388
1389         return portname;
1390 }
1391
1392 string
1393 AudioEngine::make_port_name_non_relative (string portname)
1394 {
1395         string str;
1396
1397         if (portname.find_first_of (':') != string::npos) {
1398                 return portname;
1399         }
1400
1401         str  = jack_client_name;
1402         str += ':';
1403         str += portname;
1404         
1405         return str;
1406 }
1407
1408 bool
1409 AudioEngine::is_realtime () const
1410 {
1411         if (_jack) {
1412                 return jack_is_realtime (_jack);
1413         } else {
1414                 return false;
1415         }
1416 }