1 #include "ardour/jack_audiobackend.h"
3 #define GET_PRIVATE_JACK_POINTER(j) jack_client_t* _priv_jack = (jack_client_t*) (j); if (!_priv_jack) { return; }
4 #define GET_PRIVATE_JACK_POINTER_RET(j,r) jack_client_t* _priv_jack = (jack_client_t*) (j); if (!_priv_jack) { return r; }
7 JACKAudioBackend::start ()
9 Glib::Threads::Mutex::Lock lm (_state_lock);
18 JACKAudioBackend::stop ()
20 GET_PRIVATE_JACK_POINTER_RET (_jack, -1);
23 Glib::Threads::Mutex::Lock lm (_process_lock);
24 jack_client_close (_priv_jack);
30 _raw_buffer_sizes.clear();
36 JACKAudioBackend::pause ()
38 GET_PRIVATE_JACK_POINTER_RET (_jack, -1);
41 jack_deactivate (_priv_jack);
48 JACKAudioBackend::freewheel (bool onoff)
50 GET_PRIVATE_JACK_POINTER_RET (_jack, -1);
52 if (onoff == _freewheeling) {
53 /* already doing what has been asked for */
58 return jack_set_freewheel (_priv_jack, onoff);
62 JACKAudioBackend::set_parameters (const Parameters& params)
68 JACKAudioBackend::get_parameters (Parameters& params) const
73 /*--- private support methods ---*/
76 JACKAudioBackend::connect_to_jack (string client_name, string session_uuid)
78 EnvironmentalProtectionAgency* global_epa = EnvironmentalProtectionAgency::get_global_epa ();
79 boost::scoped_ptr<EnvironmentalProtectionAgency> current_epa;
82 /* revert all environment settings back to whatever they were when ardour started
86 current_epa.reset (new EnvironmentalProtectionAgency(true)); /* will restore settings when we leave scope */
87 global_epa->restore ();
90 jack_client_name = client_name; /* might be reset below */
91 #ifdef HAVE_JACK_SESSION
92 if (!session_uuid.empty())
93 _jack = jack_client_open (jack_client_name.c_str(), JackSessionID, &status, session_uuid.c_str());
96 _jack = jack_client_open (jack_client_name.c_str(), JackNullOption, &status, 0);
99 // error message is not useful here
103 GET_PRIVATE_JACK_POINTER_RET (_jack, -1);
105 if (status & JackNameNotUnique) {
106 jack_client_name = jack_get_client_name (_priv_jack);
113 JACKAudioBackend::disconnect_from_jack ()
117 AudioEngine::reconnect_to_jack ()
120 disconnect_from_jack ();
121 /* XXX give jackd a chance */
122 Glib::usleep (250000);
125 if (connect_to_jack (jack_client_name, "")) {
126 error << _("failed to connect to JACK") << endmsg;
132 boost::shared_ptr<Ports> p = ports.reader ();
134 for (i = p->begin(); i != p->end(); ++i) {
135 if (i->second->reestablish ()) {
146 GET_PRIVATE_JACK_POINTER_RET (_jack,-1);
148 MIDI::Manager::instance()->reestablish (_priv_jack);
151 _session->reset_jack_connection (_priv_jack);
152 jack_bufsize_callback (jack_get_buffer_size (_priv_jack));
153 _session->set_frame_rate (jack_get_sample_rate (_priv_jack));
156 last_monitor_check = 0;
158 set_jack_callbacks ();
160 if (jack_activate (_priv_jack) == 0) {
167 /* re-establish connections */
169 for (i = p->begin(); i != p->end(); ++i) {
170 i->second->reconnect ();
173 MIDI::Manager::instance()->reconnect ();
175 Running (); /* EMIT SIGNAL*/
177 start_metering_thread ();
183 JACKAudioBackend::request_buffer_size (pframes_t nframes)
185 GET_PRIVATE_JACK_POINTER_RET (_jack, -1);
187 if (nframes == jack_get_buffer_size (_priv_jack)) {
191 return jack_set_buffer_size (_priv_jack, nframes);
194 /* --- TRANSPORT STATE MANAGEMENT --- */
197 AudioEngine::transport_stop ()
199 GET_PRIVATE_JACK_POINTER (_jack);
200 jack_transport_stop (_priv_jack);
204 AudioEngine::transport_start ()
206 GET_PRIVATE_JACK_POINTER (_jack);
207 jack_transport_start (_priv_jack);
211 AudioEngine::transport_locate (framepos_t where)
213 GET_PRIVATE_JACK_POINTER (_jack);
214 jack_transport_locate (_priv_jack, where);
218 AudioEngine::transport_frame () const
220 GET_PRIVATE_JACK_POINTER_RET (_jack, 0);
221 return jack_get_current_transport_frame (_priv_jack);
224 AudioEngine::TransportState
225 AudioEngine::transport_state ()
227 GET_PRIVATE_JACK_POINTER_RET (_jack, ((TransportState) JackTransportStopped));
229 return (TransportState) jack_transport_query (_priv_jack, &pos);
236 ardour_jack_error (const char* msg)
238 error << "JACK: " << msg << endmsg;
242 JACKAudioBackend::set_jack_callbacks ()
244 GET_PRIVATE_JACK_POINTER (_jack);
246 if (jack_on_info_shutdown) {
247 jack_on_info_shutdown (_priv_jack, halted_info, this);
249 jack_on_shutdown (_priv_jack, halted, this);
252 jack_set_thread_init_callback (_priv_jack, _thread_init_callback, this);
253 jack_set_process_thread (_priv_jack, _process_thread, this);
254 jack_set_sample_rate_callback (_priv_jack, _sample_rate_callback, this);
255 jack_set_buffer_size_callback (_priv_jack, _bufsize_callback, this);
256 jack_set_graph_order_callback (_priv_jack, _graph_order_callback, this);
257 jack_set_port_registration_callback (_priv_jack, _registration_callback, this);
258 jack_set_port_connect_callback (_priv_jack, _connect_callback, this);
259 jack_set_xrun_callback (_priv_jack, _xrun_callback, this);
260 jack_set_sync_callback (_priv_jack, _jack_sync_callback, this);
261 jack_set_freewheel_callback (_priv_jack, _freewheel_callback, this);
263 if (_session && _session->config.get_jack_time_master()) {
264 jack_set_timebase_callback (_priv_jack, 0, _jack_timebase_callback, this);
267 #ifdef HAVE_JACK_SESSION
268 if( jack_set_session_callback)
269 jack_set_session_callback (_priv_jack, _session_callback, this);
272 if (jack_set_latency_callback) {
273 jack_set_latency_callback (_priv_jack, _latency_callback, this);
276 jack_set_error_function (ardour_jack_error);
280 JACKAudioBackend::_jack_timebase_callback (jack_transport_state_t state, pframes_t nframes,
281 jack_position_t* pos, int new_position, void *arg)
283 static_cast<AudioEngine*> (arg)->jack_timebase_callback (state, nframes, pos, new_position);
287 JACKAudioBackend::jack_timebase_callback (jack_transport_state_t state, pframes_t nframes,
288 jack_position_t* pos, int new_position)
290 if (_jack && _session && _session->synced_to_jack()) {
291 _session->jack_timebase_callback (state, nframes, pos, new_position);
296 JACKAudioBackend::_jack_sync_callback (jack_transport_state_t state, jack_position_t* pos, void* arg)
298 return static_cast<AudioEngine*> (arg)->jack_sync_callback (state, pos);
302 JACKAudioBackend::jack_sync_callback (jack_transport_state_t state, jack_position_t* pos)
304 if (_jack && _session) {
305 return _session->jack_sync_callback (state, pos);
312 JACKAudioBackend::_xrun_callback (void *arg)
314 AudioEngine* ae = static_cast<AudioEngine*> (arg);
315 if (ae->connected()) {
316 ae->Xrun (); /* EMIT SIGNAL */
321 #ifdef HAVE_JACK_SESSION
323 JACKAudioBackend::_session_callback (jack_session_event_t *event, void *arg)
325 AudioEngine* ae = static_cast<AudioEngine*> (arg);
326 if (ae->connected()) {
327 ae->JackSessionEvent ( event ); /* EMIT SIGNAL */
333 JACKAudioBackend::_graph_order_callback (void *arg)
335 AudioEngine* ae = static_cast<AudioEngine*> (arg);
337 if (ae->connected() && !ae->port_remove_in_progress) {
338 ae->GraphReordered (); /* EMIT SIGNAL */
345 JACKAudioBackend::_freewheel_callback (int onoff, void *arg)
347 static_cast<AudioEngine*>(arg)->freewheel_callback (onoff);
351 JACKAudioBackend::freewheel_callback (int onoff)
353 _freewheeling = onoff;
356 _pre_freewheel_mmc_enabled = MIDI::Manager::instance()->mmc()->send_enabled ();
357 MIDI::Manager::instance()->mmc()->enable_send (false);
359 MIDI::Manager::instance()->mmc()->enable_send (_pre_freewheel_mmc_enabled);
364 JACKAudioBackend::_registration_callback (jack_port_id_t /*id*/, int /*reg*/, void* arg)
366 AudioEngine* ae = static_cast<AudioEngine*> (arg);
368 if (!ae->port_remove_in_progress) {
369 ae->PortRegisteredOrUnregistered (); /* EMIT SIGNAL */
374 JACKAudioBackend::_latency_callback (jack_latency_callback_mode_t mode, void* arg)
376 return static_cast<AudioEngine *> (arg)->jack_latency_callback (mode);
380 JACKAudioBackend::_connect_callback (jack_port_id_t id_a, jack_port_id_t id_b, int conn, void* arg)
382 AudioEngine* ae = static_cast<AudioEngine*> (arg);
383 ae->connect_callback (id_a, id_b, conn);
387 JACKAudioBackend::connect_callback (jack_port_id_t id_a, jack_port_id_t id_b, int conn)
389 if (port_remove_in_progress) {
393 GET_PRIVATE_JACK_POINTER (_jack);
395 jack_port_t* jack_port_a = jack_port_by_id (_priv_jack, id_a);
396 jack_port_t* jack_port_b = jack_port_by_id (_priv_jack, id_b);
398 boost::shared_ptr<Port> port_a;
399 boost::shared_ptr<Port> port_b;
401 boost::shared_ptr<Ports> pr = ports.reader ();
404 x = pr->find (make_port_name_relative (jack_port_name (jack_port_a)));
405 if (x != pr->end()) {
409 x = pr->find (make_port_name_relative (jack_port_name (jack_port_b)));
410 if (x != pr->end()) {
414 PortConnectedOrDisconnected (
415 port_a, jack_port_name (jack_port_a),
416 port_b, jack_port_name (jack_port_b),
417 conn == 0 ? false : true
422 JACKAudioBackend::_process_thread (void *arg)
424 return static_cast<AudioEngine *> (arg)->process_thread ();
428 JACKAudioBackend::process_thread ()
430 /* JACK doesn't do this for us when we use the wait API
433 _thread_init_callback (0);
435 _main_thread = new ProcessThread;
438 GET_PRIVATE_JACK_POINTER_RET(_jack,0);
440 pframes_t nframes = jack_cycle_wait (_priv_jack);
442 if (process_callback (nframes)) {
446 jack_cycle_signal (_priv_jack, 0);
453 JACKAudioBackend::_sample_rate_callback (pframes_t nframes, void *arg)
455 return static_cast<AudioEngine *> (arg)->jack_sample_rate_callback (nframes);
459 JACKAudioBackend::jack_sample_rate_callback (pframes_t nframes)
461 _frame_rate = nframes;
462 _usecs_per_cycle = (int) floor ((((double) frames_per_cycle() / nframes)) * 1000000.0);
464 /* check for monitor input change every 1/10th of second */
466 monitor_check_interval = nframes / 10;
467 last_monitor_check = 0;
470 _session->set_frame_rate (nframes);
473 SampleRateChanged (nframes); /* EMIT SIGNAL */
479 JACKAudioBackend::jack_latency_callback (jack_latency_callback_mode_t mode)
482 _session->update_latency (mode == JackPlaybackLatency);
487 JACKAudioBackend::_bufsize_callback (pframes_t nframes, void *arg)
489 return static_cast<AudioEngine *> (arg)->jack_bufsize_callback (nframes);
493 JACKAudioBackend::jack_bufsize_callback (pframes_t nframes)
495 /* if the size has not changed, this should be a no-op */
497 if (nframes == _buffer_size) {
501 GET_PRIVATE_JACK_POINTER_RET (_jack, 1);
503 _buffer_size = nframes;
504 _usecs_per_cycle = (int) floor ((((double) nframes / frame_rate())) * 1000000.0);
505 last_monitor_check = 0;
507 if (jack_port_type_get_buffer_size) {
508 _raw_buffer_sizes[DataType::AUDIO] = jack_port_type_get_buffer_size (_priv_jack, JACK_DEFAULT_AUDIO_TYPE);
509 _raw_buffer_sizes[DataType::MIDI] = jack_port_type_get_buffer_size (_priv_jack, JACK_DEFAULT_MIDI_TYPE);
512 /* Old version of JACK.
514 These crude guesses, see below where we try to get the right answers.
516 Note that our guess for MIDI deliberatey tries to overestimate
517 by a little. It would be nicer if we could get the actual
518 size from a port, but we have to use this estimate in the
519 event that there are no MIDI ports currently. If there are
520 the value will be adjusted below.
523 _raw_buffer_sizes[DataType::AUDIO] = nframes * sizeof (Sample);
524 _raw_buffer_sizes[DataType::MIDI] = nframes * 4 - (nframes/2);
528 Glib::Threads::Mutex::Lock lm (_process_lock);
530 boost::shared_ptr<Ports> p = ports.reader();
532 for (Ports::iterator i = p->begin(); i != p->end(); ++i) {
538 _session->set_block_size (_buffer_size);
545 JACKAudioBackend::halted_info (jack_status_t code, const char* reason, void *arg)
547 /* called from jack shutdown handler */
549 AudioEngine* ae = static_cast<AudioEngine *> (arg);
550 bool was_running = ae->_running;
552 ae->stop_metering_thread ();
554 ae->_running = false;
555 ae->_buffer_size = 0;
560 MIDI::JackMIDIPort::JackHalted (); /* EMIT SIGNAL */
561 #ifdef HAVE_JACK_ON_INFO_SHUTDOWN
563 case JackBackendError:
564 ae->Halted(reason); /* EMIT SIGNAL */
567 ae->Halted(""); /* EMIT SIGNAL */
570 ae->Halted(""); /* EMIT SIGNAL */
576 JACKAudioBackend::halted (void *arg)
578 cerr << "HALTED by JACK\n";
580 /* called from jack shutdown handler */
582 AudioEngine* ae = static_cast<AudioEngine *> (arg);
583 bool was_running = ae->_running;
585 ae->stop_metering_thread ();
587 ae->_running = false;
588 ae->_buffer_size = 0;
593 MIDI::JackMIDIPort::JackHalted (); /* EMIT SIGNAL */
594 ae->Halted(""); /* EMIT SIGNAL */