summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--libs/backends/alsa/alsa_audiobackend.cc66
-rw-r--r--libs/backends/alsa/alsa_audiobackend.h15
-rw-r--r--libs/backends/coreaudio/coreaudio_backend.cc51
-rw-r--r--libs/backends/coreaudio/coreaudio_backend.h15
-rw-r--r--libs/backends/portaudio/portaudio_backend.cc49
-rw-r--r--libs/backends/portaudio/portaudio_backend.h15
6 files changed, 175 insertions, 36 deletions
diff --git a/libs/backends/alsa/alsa_audiobackend.cc b/libs/backends/alsa/alsa_audiobackend.cc
index 292875e6f9..4e92b854e8 100644
--- a/libs/backends/alsa/alsa_audiobackend.cc
+++ b/libs/backends/alsa/alsa_audiobackend.cc
@@ -1386,6 +1386,39 @@ AlsaAudioBackend::register_system_audio_ports()
return 0;
}
+/* set playback-latency for _system_inputs
+ * and capture-latency for _system_outputs
+ */
+void
+AlsaAudioBackend::update_system_port_latecies ()
+{
+ for (std::vector<AlsaPort*>::const_iterator it = _system_inputs.begin (); it != _system_inputs.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<AlsaPort*>::const_iterator it = _system_outputs.begin (); it != _system_outputs.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+
+ for (std::vector<AlsaPort*>::const_iterator it = _system_midi_in.begin (); it != _system_midi_in.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<AlsaPort*>::const_iterator it = _system_midi_out.begin (); it != _system_midi_out.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+
+ for (AudioSlaves::iterator s = _slaves.begin (); s != _slaves.end (); ++s) {
+ if ((*s)->dead) {
+ continue;
+ }
+ for (std::vector<AlsaPort*>::const_iterator it = (*s)->inputs.begin (); it != (*s)->inputs.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<AlsaPort*>::const_iterator it = (*s)->outputs.begin (); it != (*s)->outputs.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+ }
+}
+
/* libs/ardouralsautil/devicelist.cc appends either of
* " (IO)", " (I)", or " (O)"
* depending of the device is full-duples or half-duplex
@@ -2136,6 +2169,7 @@ AlsaAudioBackend::main_process_thread ()
manager.graph_order_callback();
}
if (connections_changed || ports_changed) {
+ update_system_port_latecies (); // flush, clear
engine.latency_callback(false);
engine.latency_callback(true);
}
@@ -2339,7 +2373,6 @@ AlsaPort::~AlsaPort () {
disconnect_all ();
}
-
int AlsaPort::connect (AlsaPort *port)
{
if (!port) {
@@ -2380,7 +2413,6 @@ int AlsaPort::connect (AlsaPort *port)
return 0;
}
-
void AlsaPort::_connect (AlsaPort *port, bool callback)
{
_connections.insert (port);
@@ -2445,6 +2477,36 @@ bool AlsaPort::is_physically_connected () const
return false;
}
+void
+AlsaPort::set_latency_range (const LatencyRange &latency_range, bool for_playback)
+{
+ if (for_playback) {
+ _playback_latency_range = latency_range;
+ } else {
+ _capture_latency_range = latency_range;
+ }
+
+ for (std::set<AlsaPort*>::const_iterator it = _connections.begin (); it != _connections.end (); ++it) {
+ if ((*it)->is_physical ()) {
+ (*it)->update_connected_latency (is_input ());
+ }
+ }
+}
+
+void
+AlsaPort::update_connected_latency (bool for_playback)
+{
+ LatencyRange lr;
+ lr.min = lr.max = 0;
+ for (std::set<AlsaPort*>::const_iterator it = _connections.begin (); it != _connections.end (); ++it) {
+ LatencyRange l;
+ l = (*it)->latency_range (for_playback);
+ lr.min = std::max (lr.min, l.min);
+ lr.max = std::max (lr.max, l.max);
+ }
+ set_latency_range (lr, for_playback);
+}
+
/******************************************************************************/
AlsaAudioPort::AlsaAudioPort (AlsaAudioBackend &b, const std::string& name, PortFlags flags)
diff --git a/libs/backends/alsa/alsa_audiobackend.h b/libs/backends/alsa/alsa_audiobackend.h
index 2cbc3b04a3..f6887fe346 100644
--- a/libs/backends/alsa/alsa_audiobackend.h
+++ b/libs/backends/alsa/alsa_audiobackend.h
@@ -99,17 +99,9 @@ class AlsaPort {
return for_playback ? _playback_latency_range : _capture_latency_range;
}
- void set_latency_range (const LatencyRange &latency_range, bool for_playback)
- {
- if (for_playback)
- {
- _playback_latency_range = latency_range;
- }
- else
- {
- _capture_latency_range = latency_range;
- }
- }
+ void set_latency_range (const LatencyRange &latency_range, bool for_playback);
+
+ void update_connected_latency (bool for_playback);
private:
AlsaAudioBackend &_alsa_backend;
@@ -419,6 +411,7 @@ class AlsaAudioBackend : public AudioBackend {
int register_system_audio_ports ();
int register_system_midi_ports (const std::string device = "");
void unregister_ports (bool system_only = false);
+ void update_system_port_latecies ();
std::vector<AlsaPort *> _system_inputs;
std::vector<AlsaPort *> _system_outputs;
diff --git a/libs/backends/coreaudio/coreaudio_backend.cc b/libs/backends/coreaudio/coreaudio_backend.cc
index 0e0f33a5d9..fc94145ed5 100644
--- a/libs/backends/coreaudio/coreaudio_backend.cc
+++ b/libs/backends/coreaudio/coreaudio_backend.cc
@@ -1163,6 +1163,24 @@ CoreAudioBackend::register_system_audio_ports()
}
void
+CoreAudioBackend::update_system_port_latecies ()
+{
+ for (std::vector<CoreBackendPort*>::const_iterator it = _system_inputs.begin (); it != _system_inputs.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<CoreBackendPort*>::const_iterator it = _system_outputs.begin (); it != _system_outputs.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+
+ for (std::vector<CoreBackendPort*>::const_iterator it = _system_midi_in.begin (); it != _system_midi_in.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<CoreBackendPort*>::const_iterator it = _system_midi_out.begin (); it != _system_midi_out.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+}
+
+void
CoreAudioBackend::coremidi_rediscover()
{
if (!_run) { return; }
@@ -1644,6 +1662,7 @@ CoreAudioBackend::pre_process ()
manager.graph_order_callback();
}
if (connections_changed || ports_changed) {
+ update_system_port_latecies ();
engine.latency_callback(false);
engine.latency_callback(true);
}
@@ -2081,7 +2100,6 @@ void CoreBackendPort::_disconnect (CoreBackendPort *port, bool callback)
}
}
-
void CoreBackendPort::disconnect_all ()
{
while (!_connections.empty ()) {
@@ -2108,6 +2126,37 @@ bool CoreBackendPort::is_physically_connected () const
return false;
}
+void
+CoreBackendPort::set_latency_range (const LatencyRange &latency_range, bool for_playback)
+{
+ if (for_playback) {
+ _playback_latency_range = latency_range;
+ } else {
+ _capture_latency_range = latency_range;
+ }
+
+ for (std::set<CoreBackendPort*>::const_iterator it = _connections.begin (); it != _connections.end (); ++it) {
+ if ((*it)->is_physical ()) {
+ (*it)->update_connected_latency (is_input ());
+ }
+ }
+}
+
+void
+CoreBackendPort::update_connected_latency (bool for_playback)
+{
+ LatencyRange lr;
+ lr.min = lr.max = 0;
+ const std::set<CoreBackendPort *>& cp = get_connections ();
+ for (std::set<CoreBackendPort*>::const_iterator it = cp.begin (); it != cp.end (); ++it) {
+ LatencyRange l;
+ l = (*it)->latency_range (for_playback);
+ lr.min = std::max (lr.min, l.min);
+ lr.max = std::max (lr.max, l.max);
+ }
+ set_latency_range (lr, for_playback);
+}
+
/******************************************************************************/
CoreAudioPort::CoreAudioPort (CoreAudioBackend &b, const std::string& name, PortFlags flags)
diff --git a/libs/backends/coreaudio/coreaudio_backend.h b/libs/backends/coreaudio/coreaudio_backend.h
index 5d8c88c3db..7e8c55f2eb 100644
--- a/libs/backends/coreaudio/coreaudio_backend.h
+++ b/libs/backends/coreaudio/coreaudio_backend.h
@@ -96,17 +96,9 @@ class CoreBackendPort {
return for_playback ? _playback_latency_range : _capture_latency_range;
}
- void set_latency_range (const LatencyRange &latency_range, bool for_playback)
- {
- if (for_playback)
- {
- _playback_latency_range = latency_range;
- }
- else
- {
- _capture_latency_range = latency_range;
- }
- }
+ void set_latency_range (const LatencyRange &latency_range, bool for_playback);
+
+ void update_connected_latency (bool for_playback);
private:
CoreAudioBackend &_osx_backend;
@@ -463,6 +455,7 @@ class CoreAudioBackend : public AudioBackend {
PortHandle add_port (const std::string& shortname, ARDOUR::DataType, ARDOUR::PortFlags);
int register_system_audio_ports ();
void unregister_ports (bool system_only = false);
+ void update_system_port_latecies ();
std::vector<CoreBackendPort *> _system_inputs;
std::vector<CoreBackendPort *> _system_outputs;
diff --git a/libs/backends/portaudio/portaudio_backend.cc b/libs/backends/portaudio/portaudio_backend.cc
index be43e67a62..7a65bdcc38 100644
--- a/libs/backends/portaudio/portaudio_backend.cc
+++ b/libs/backends/portaudio/portaudio_backend.cc
@@ -1500,6 +1500,24 @@ PortAudioBackend::unregister_ports (bool system_only)
}
}
+void
+PortAudioBackend::update_system_port_latecies ()
+{
+ for (std::vector<PamPort*>::const_iterator it = _system_inputs.begin (); it != _system_inputs.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<PamPort*>::const_iterator it = _system_outputs.begin (); it != _system_outputs.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+
+ for (std::vector<PamPort*>::const_iterator it = _system_midi_in.begin (); it != _system_midi_in.end (); ++it) {
+ (*it)->update_connected_latency (true);
+ }
+ for (std::vector<PamPort*>::const_iterator it = _system_midi_out.begin (); it != _system_midi_out.end (); ++it) {
+ (*it)->update_connected_latency (false);
+ }
+}
+
int
PortAudioBackend::connect (const std::string& src, const std::string& dst)
{
@@ -2132,6 +2150,7 @@ PortAudioBackend::process_port_connection_changes ()
manager.graph_order_callback();
}
if (connections_changed || ports_changed) {
+ update_system_port_latecies ();
engine.latency_callback(false);
engine.latency_callback(true);
}
@@ -2322,6 +2341,36 @@ bool PamPort::is_physically_connected () const
return false;
}
+void
+PamPort::set_latency_range (const LatencyRange &latency_range, bool for_playback)
+{
+ if (for_playback) {
+ _playback_latency_range = latency_range;
+ } else {
+ _capture_latency_range = latency_range;
+ }
+
+ for (std::vector<PamPort*>::const_iterator it = _connections.begin (); it != _connections.end (); ++it) {
+ if ((*it)->is_physical ()) {
+ (*it)->update_connected_latency (is_input ());
+ }
+ }
+}
+
+void
+PamPort::update_connected_latency (bool for_playback)
+{
+ LatencyRange lr;
+ lr.min = lr.max = 0;
+ for (std::set<PamPort*>::const_iterator it = _connections.begin (); it != _connections.end (); ++it) {
+ LatencyRange l;
+ l = (*it)->latency_range (for_playback);
+ lr.min = std::max (lr.min, l.min);
+ lr.max = std::max (lr.max, l.max);
+ }
+ set_latency_range (lr, for_playback);
+}
+
/******************************************************************************/
PortAudioPort::PortAudioPort (PortAudioBackend &b, const std::string& name, PortFlags flags)
diff --git a/libs/backends/portaudio/portaudio_backend.h b/libs/backends/portaudio/portaudio_backend.h
index 336621f4ff..bc493101fc 100644
--- a/libs/backends/portaudio/portaudio_backend.h
+++ b/libs/backends/portaudio/portaudio_backend.h
@@ -93,17 +93,9 @@ class PamPort { // PortAudio / PortMidi Backend Port
return for_playback ? _playback_latency_range : _capture_latency_range;
}
- void set_latency_range (const LatencyRange &latency_range, bool for_playback)
- {
- if (for_playback)
- {
- _playback_latency_range = latency_range;
- }
- else
- {
- _capture_latency_range = latency_range;
- }
- }
+ void set_latency_range (const LatencyRange &latency_range, bool for_playback);
+
+ void update_connected_latency (bool for_playback);
private:
PortAudioBackend &_osx_backend;
@@ -436,6 +428,7 @@ class PortAudioBackend : public AudioBackend {
int register_system_audio_ports ();
int register_system_midi_ports ();
void unregister_ports (bool system_only = false);
+ void update_system_port_latecies ();
std::vector<PamPort *> _ports;
std::vector<PamPort *> _system_inputs;