[PATCH 1/3] [latency api] first go on latency api

classic Classic list List threaded Threaded
37 messages Options
12
Reply | Threaded
Open this post in threaded view
|

[PATCH 1/3] [latency api] first go on latency api

torbenh
---
 jack/internal.h  |    4 ++-
 jack/jack.h      |   23 ++++++++++++++++++
 jack/port.h      |    2 +
 jack/types.h     |   37 +++++++++++++++++++++++++++++
 jackd/engine.c   |   36 +++++++++++++++++++++++++++-
 libjack/client.c |   68 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
 libjack/local.h  |    2 +
 libjack/port.c   |   25 +++++++++++++++++++
 8 files changed, 195 insertions(+), 2 deletions(-)

diff --git a/jack/internal.h b/jack/internal.h
index c6107c8..c2009e7 100644
--- a/jack/internal.h
+++ b/jack/internal.h
@@ -219,7 +219,8 @@ typedef enum  {
   StopFreewheel,
   ClientRegistered,
   ClientUnregistered,
-  SaveSession
+  SaveSession,
+  LatencyCallback
 } JackEventType;
 
 typedef struct {
@@ -298,6 +299,7 @@ typedef volatile struct {
     volatile uint8_t client_register_cbset;
     volatile uint8_t thread_cb_cbset;
     volatile uint8_t session_cbset;
+    volatile uint8_t latency_cbset;
 
 } POST_PACKED_STRUCTURE jack_client_control_t;
 
diff --git a/jack/jack.h b/jack/jack.h
index c80f879..ab79636 100644
--- a/jack/jack.h
+++ b/jack/jack.h
@@ -406,6 +406,16 @@ int jack_set_graph_order_callback (jack_client_t *,
  */
 int jack_set_xrun_callback (jack_client_t *,
     JackXRunCallback xrun_callback, void *arg) JACK_OPTIONAL_WEAK_EXPORT;
+
+/**
+ * Tell the JACK server to call @a latency_callback whenever the
+ * port latencies need to be recalculated.
+ *
+ * @return 0 on success, otherwise a non-zero error code
+ */
+int jack_set_latency_callback (jack_client_t *,
+   JackLatencyCallback latency_callback,
+   void *) JACK_OPTIONAL_WEAK_EXPORT;
 /*@}*/
 
 /**
@@ -691,6 +701,19 @@ jack_nframes_t jack_port_get_total_latency (jack_client_t *,
 void jack_port_set_latency (jack_port_t *, jack_nframes_t) JACK_OPTIONAL_WEAK_EXPORT;
 
 /**
+ * get the new latency, either capture latency or playback latency.
+ * this is normally used in the LatencyCallback.
+ * and therefor safe to execute from callbacks.
+ */
+jack_nframes_t jack_port_get_new_latency (jack_port_t *port, jack_latency_callback_mode_t mode) JACK_WEAK_EXPORT;
+
+
+/**
+ * set the new latency, either capture latency or playback latency.
+ */
+void jack_port_set_new_latency (jack_port_t *port, jack_latency_callback_mode_t mode, jack_nframes_t latency) JACK_WEAK_EXPORT;
+
+/**
  * Request a complete recomputation of a port's total latency. This
  * can be called by a client that has just changed the internal
  * latency of its port using  jack_port_set_latency
diff --git a/jack/port.h b/jack/port.h
index 796a19a..e30b6ee 100644
--- a/jack/port.h
+++ b/jack/port.h
@@ -121,6 +121,8 @@ typedef struct _jack_port_shared {
 
     volatile jack_nframes_t  latency;
     volatile jack_nframes_t  total_latency;
+    volatile jack_nframes_t  playback_latency;
+    volatile jack_nframes_t  capture_latency;
     volatile uint8_t     monitor_requests;
 
     char     has_mixdown; /* port has a mixdown function */
diff --git a/jack/types.h b/jack/types.h
index 91d2523..d11e876 100644
--- a/jack/types.h
+++ b/jack/types.h
@@ -220,6 +220,43 @@ enum JackStatus {
 typedef enum JackStatus jack_status_t;
 
 /**
+ *  @ref jack_latency_callback_mode_t
+ */
+enum JackLatencyCallbackMode {
+
+     /**
+      * Latency Callback for Capture Latency.
+      * Input Ports have their latency value setup.
+      * In the Callback the client needs to set the latency of the output ports
+      */
+     JackCaptureLatency,
+
+     /**
+      * Latency Callback for Playback Latency.
+      * Output Ports have their latency value setup.
+      * In the Callback the client needs to set the latency of the input ports
+      */
+     JackPlaybackLatency
+
+};
+
+/**
+ *  Type of Latency Callback (Capture or Playback)
+ */
+typedef enum JackLatencyCallbackMode jack_latency_callback_mode_t;
+
+/**
+ * Prototype for the client supplied function that is called
+ * by the engine when port latencies need to be recalculated
+ *
+ * @param mode playback or capture latency
+ * @param arg pointer to a client supplied data
+ *
+ * @return zero on success, non-zero on error
+ */
+typedef int  (*JackLatencyCallback)(jack_latency_callback_mode_t mode, void *arg);
+
+/**
  * Prototype for the client supplied function that is called
  * by the engine anytime there is work to be done.
  *
diff --git a/jackd/engine.c b/jackd/engine.c
index 4f05bec..659e431 100644
--- a/jackd/engine.c
+++ b/jackd/engine.c
@@ -3268,6 +3268,39 @@ jack_compute_all_port_total_latencies (jack_engine_t *engine)
  }
 }
 
+static void
+jack_compute_new_latency (jack_engine_t *engine)
+{
+ JSList *node;
+ JSList *reverse_list = NULL;
+
+ jack_event_t event;
+ event.type = LatencyCallback;
+ event.x.n  = 0;
+
+ /* iterate over all clients in graph order, and emit
+ * capture latency callback.
+ * also builds up list in reverse graph order.
+ */
+ for (node = engine->clients; node; node = jack_slist_next(node)) {
+
+                jack_client_internal_t* client = (jack_client_internal_t *) node->data;
+ reverse_list = jack_slist_prepend (reverse_list, client);
+ jack_deliver_event (engine, client, &event);
+ }
+
+ /* now issue playback latency callbacks in reverse graphorder
+ */
+ event.x.n  = 1;
+ for (node = reverse_list; node; node = jack_slist_next(node)) {
+                jack_client_internal_t* client = (jack_client_internal_t *) node->data;
+ jack_deliver_event (engine, client, &event);
+ }
+
+ jack_slist_free (reverse_list);
+}
+
+
 /* How the sort works:
  *
  * Each client has a "sortfeeds" list of clients indicating which clients
@@ -3294,7 +3327,7 @@ jack_compute_all_port_total_latencies (jack_engine_t *engine)
  * This is used to detect whether the graph has become acyclic.
  *
  */
-
+
 void
 jack_sort_graph (jack_engine_t *engine)
 {
@@ -3305,6 +3338,7 @@ jack_sort_graph (jack_engine_t *engine)
    (JCompareFunc) jack_client_sort);
  jack_compute_all_port_total_latencies (engine);
  jack_rechain_graph (engine);
+ jack_compute_new_latency (engine);
  VERBOSE (engine, "-- jack_sort_graph");
 }
 
diff --git a/libjack/client.c b/libjack/client.c
index de0048a..adca140 100644
--- a/libjack/client.c
+++ b/libjack/client.c
@@ -541,6 +541,57 @@ jack_client_handle_session_callback (jack_client_t *client, jack_event_t *event)
  }
  return 1;
 }
+
+static void
+jack_port_recalculate_latency (jack_port_t *port, jack_latency_callback_mode_t mode)
+{
+ jack_nframes_t max_latency = 0;
+ JSList *node;
+
+ pthread_mutex_lock (&port->connection_lock);
+ for (node = port->connections; node; node = jack_slist_next (node)) {
+ jack_port_t *other = node->data;
+ jack_nframes_t other_latency = jack_port_get_new_latency (other, mode);
+
+ if (other_latency > max_latency)
+ max_latency = other_latency;
+
+ }
+ pthread_mutex_unlock (&port->connection_lock);
+
+ jack_port_set_new_latency (port, mode, max_latency);
+}
+
+int
+jack_client_handle_latency_callback (jack_client_t *client, jack_event_t *event)
+{
+ jack_latency_callback_mode_t mode = (event->x.n==0) ? JackCaptureLatency : JackPlaybackLatency;
+ JSList *node;
+
+ /* first setup all latency values of the ports.
+ * this is based on the connections of the ports.
+ */
+ for (node = client->ports; node; node = jack_slist_next (node)) {
+ jack_port_t *port = node->data;
+
+ if ((jack_port_flags (port) & JackPortIsOutput) && (mode == JackPlaybackLatency)) {
+ jack_port_recalculate_latency (port, mode);
+ }
+ if ((jack_port_flags (port) & JackPortIsInput) && (mode == JackCaptureLatency)) {
+ jack_port_recalculate_latency (port, mode);
+ }
+ }
+
+ if (! client->control->latency_cbset) {
+ /*
+ * default action is to assume all ports depend on each other.
+ * then always take the maximum latency.
+ */
+ return 0;
+ }
+
+ return client->latency_cb ( mode, client->latency_cb_arg);
+}
 #if JACK_USE_MACH_THREADS
 
 static int
@@ -1661,6 +1712,9 @@ jack_client_process_events (jack_client_t* client)
  case SaveSession:
  status = jack_client_handle_session_callback (client, &event );
  break;
+ case LatencyCallback:
+ status = jack_client_handle_latency_callback (client, &event );
+ break;
  }
 
  DEBUG ("client has dealt with the event, writing "
@@ -2494,6 +2548,20 @@ jack_set_graph_order_callback (jack_client_t *client,
  return 0;
 }
 
+int
+jack_set_latency_callback (jack_client_t *client,
+       JackLatencyCallback callback, void *arg)
+{
+ if (client->control->active) {
+ jack_error ("You cannot set callbacks on an active client.");
+ return -1;
+ }
+ client->latency_cb = callback;
+ client->latency_cb_arg = arg;
+ client->control->latency_cbset = (callback != NULL);
+ return 0;
+}
+
 int jack_set_xrun_callback (jack_client_t *client,
     JackXRunCallback callback, void *arg)
 {
diff --git a/libjack/local.h b/libjack/local.h
index 1168676..9cc3005 100644
--- a/libjack/local.h
+++ b/libjack/local.h
@@ -75,6 +75,8 @@ struct _jack_client {
     void *thread_cb_arg;
     JackSessionCallback session_cb;
     void *session_cb_arg;
+    JackLatencyCallback latency_cb;
+    void *latency_cb_arg;
 
     /* external clients: set by libjack
      * internal clients: set by engine */
diff --git a/libjack/port.c b/libjack/port.c
index 1f7053c..00f08ad 100644
--- a/libjack/port.c
+++ b/libjack/port.c
@@ -522,6 +522,14 @@ void
 jack_port_set_latency (jack_port_t *port, jack_nframes_t nframes)
 {
  port->shared->latency = nframes;
+
+ /* setup the new latency values here,
+ * so we dont need to change the backend codes.
+ */
+ if (port->shared->flags & JackPortIsOutput)
+ port->shared->capture_latency = nframes;
+ if (port->shared->flags & JackPortIsInput)
+ port->shared->playback_latency = nframes;
 }
 
 void *
@@ -794,6 +802,23 @@ jack_port_unset_alias (jack_port_t *port, const char *alias)
  return 0;
 }
 
+void
+jack_port_set_new_latency (jack_port_t *port, jack_latency_callback_mode_t mode, jack_nframes_t latency)
+{
+ if (mode == JackCaptureLatency)
+ port->shared->capture_latency = latency;
+ else
+ port->shared->playback_latency = latency;
+}
+
+jack_nframes_t
+jack_port_get_new_latency (jack_port_t *port, jack_latency_callback_mode_t mode)
+{
+ if (mode == JackCaptureLatency)
+ return port->shared->capture_latency;
+ else
+ return port->shared->playback_latency;
+}
 
 /* AUDIO PORT SUPPORT */
 
--
1.7.2.3

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

[PATCH 2/3] [latency api] add latent test client for latency api

torbenh
---
 example-clients/Makefile.am     |    5 +
 example-clients/latent_client.c |  204 +++++++++++++++++++++++++++++++++++++++
 2 files changed, 209 insertions(+), 0 deletions(-)
 create mode 100644 example-clients/latent_client.c

diff --git a/example-clients/Makefile.am b/example-clients/Makefile.am
index d859395..dd64852 100644
--- a/example-clients/Makefile.am
+++ b/example-clients/Makefile.am
@@ -20,6 +20,7 @@ bin_PROGRAMS = jack_simple_client \
        jack_showtime \
        jack_midisine \
        jack_midiseq \
+       jack_latent_client \
        $(JACKREC)
 
 if HAVE_SNDFILE
@@ -62,6 +63,10 @@ jack_midisine_SOURCES = midisine.c
 jack_midisine_LDFLAGS = @OS_LDFLAGS@
 jack_midisine_LDADD = $(top_builddir)/libjack/libjack.la
 
+jack_latent_client_SOURCES = latent_client.c
+jack_latent_client_LDFLAGS = @OS_LDFLAGS@
+jack_latent_client_LDADD = $(top_builddir)/libjack/libjack.la
+
 if HAVE_SNDFILE
 jack_rec_SOURCES = capture_client.c
 jack_rec_LDFLAGS = @SNDFILE_LIBS@ @OS_LDFLAGS@
diff --git a/example-clients/latent_client.c b/example-clients/latent_client.c
new file mode 100644
index 0000000..73c8e29
--- /dev/null
+++ b/example-clients/latent_client.c
@@ -0,0 +1,204 @@
+/** @file simple_client.c
+ *
+ * @brief This simple client demonstrates the most basic features of JACK
+ * as they would be used by many applications.
+ */
+
+#include <stdio.h>
+#include <errno.h>
+#include <unistd.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <jack/jack.h>
+
+jack_port_t *input_port;
+jack_port_t *output_port;
+jack_client_t *client;
+
+jack_default_audio_sample_t *delay_line;
+jack_nframes_t delay_index;
+jack_nframes_t latency = 1024;
+
+/**
+ * The process callback for this JACK application is called in a
+ * special realtime thread once for each audio cycle.
+ *
+ * This client does nothing more than copy data from its input
+ * port to its output port. It will exit when stopped by
+ * the user (e.g. using Ctrl-C on a unix-ish operating system)
+ */
+int
+process (jack_nframes_t nframes, void *arg)
+{
+ jack_default_audio_sample_t *in, *out;
+ int k;
+
+ in = jack_port_get_buffer (input_port, nframes);
+ out = jack_port_get_buffer (output_port, nframes);
+
+ for (k=0; k<nframes; k++) {
+ out[k] = delay_line[delay_index];
+ delay_line[delay_index] = in[k];
+ delay_index = (delay_index + 1) % latency;
+ }
+
+ return 0;      
+}
+
+int
+latency_cb (jack_latency_callback_mode_t mode, void *arg)
+{
+ if (mode == JackCaptureLatency) {
+ jack_port_set_new_latency (output_port, mode,
+           jack_port_get_new_latency (input_port, mode) + latency);
+ } else {
+ jack_port_set_new_latency (input_port, mode,
+           jack_port_get_new_latency (output_port, mode) + latency);
+ }
+
+ return 0;
+}
+
+/**
+ * JACK calls this shutdown_callback if the server ever shuts down or
+ * decides to disconnect the client.
+ */
+void
+jack_shutdown (void *arg)
+{
+ exit (1);
+}
+
+int
+main (int argc, char *argv[])
+{
+ const char **ports;
+ const char *client_name = "latent";
+ const char *server_name = NULL;
+ jack_options_t options = JackNullOption;
+ jack_status_t status;
+
+
+ if (argc == 2)
+ latency = atoi(argv[1]);
+
+ delay_line = malloc( latency * sizeof(jack_default_audio_sample_t));
+ if (delay_line == NULL) {
+ fprintf (stderr, "no memory");
+ exit(1);
+ }
+
+ memset (delay_line, 0, latency * sizeof(jack_default_audio_sample_t));
+
+ /* open a client connection to the JACK server */
+
+ client = jack_client_open (client_name, options, &status, server_name);
+ if (client == NULL) {
+ fprintf (stderr, "jack_client_open() failed, "
+ "status = 0x%2.0x\n", status);
+ if (status & JackServerFailed) {
+ fprintf (stderr, "Unable to connect to JACK server\n");
+ }
+ exit (1);
+ }
+ if (status & JackServerStarted) {
+ fprintf (stderr, "JACK server started\n");
+ }
+ if (status & JackNameNotUnique) {
+ client_name = jack_get_client_name(client);
+ fprintf (stderr, "unique name `%s' assigned\n", client_name);
+ }
+
+ /* tell the JACK server to call `process()' whenever
+   there is work to be done.
+ */
+
+ jack_set_process_callback (client, process, 0);
+
+ /* tell the JACK server to call `latency()' whenever
+   the latency needs to be recalculated.
+ */
+ jack_set_latency_callback (client, latency_cb, 0);
+
+ /* tell the JACK server to call `jack_shutdown()' if
+   it ever shuts down, either entirely, or if it
+   just decides to stop calling us.
+ */
+
+ jack_on_shutdown (client, jack_shutdown, 0);
+
+ /* display the current sample rate.
+ */
+
+ printf ("engine sample rate: %" PRIu32 "\n",
+ jack_get_sample_rate (client));
+
+ /* create two ports */
+
+ input_port = jack_port_register (client, "input",
+ JACK_DEFAULT_AUDIO_TYPE,
+ JackPortIsInput, 0);
+ output_port = jack_port_register (client, "output",
+  JACK_DEFAULT_AUDIO_TYPE,
+  JackPortIsOutput, 0);
+
+ if ((input_port == NULL) || (output_port == NULL)) {
+ fprintf(stderr, "no more JACK ports available\n");
+ exit (1);
+ }
+
+ /* Tell the JACK server that we are ready to roll.  Our
+ * process() callback will start running now. */
+
+ if (jack_activate (client)) {
+ fprintf (stderr, "cannot activate client");
+ exit (1);
+ }
+
+ /* Connect the ports.  You can't do this before the client is
+ * activated, because we can't make connections to clients
+ * that aren't running.  Note the confusing (but necessary)
+ * orientation of the driver backend ports: playback ports are
+ * "input" to the backend, and capture ports are "output" from
+ * it.
+ */
+
+ ports = jack_get_ports (client, NULL, NULL,
+ JackPortIsPhysical|JackPortIsOutput);
+ if (ports == NULL) {
+ fprintf(stderr, "no physical capture ports\n");
+ exit (1);
+ }
+
+ if (jack_connect (client, ports[0], jack_port_name (input_port))) {
+ fprintf (stderr, "cannot connect input ports\n");
+ }
+
+ free (ports);
+
+ ports = jack_get_ports (client, NULL, NULL,
+ JackPortIsPhysical|JackPortIsInput);
+ if (ports == NULL) {
+ fprintf(stderr, "no physical playback ports\n");
+ exit (1);
+ }
+
+ if (jack_connect (client, jack_port_name (output_port), ports[0])) {
+ fprintf (stderr, "cannot connect output ports\n");
+ }
+
+ free (ports);
+
+ /* keep running until stopped by the user */
+
+ sleep (-1);
+
+ /* this is never reached but if the program
+   had some other way to exit besides being killed,
+   they would be important to call.
+ */
+
+ jack_client_close (client);
+ exit (0);
+}
--
1.7.2.3

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

[PATCH 3/3] [latency api] also print playback and capture latency in jack_lsp

torbenh
In reply to this post by torbenh
---
 tools/lsp.c |    4 ++++
 1 files changed, 4 insertions(+), 0 deletions(-)

diff --git a/tools/lsp.c b/tools/lsp.c
index 2d449db..18f05c7 100644
--- a/tools/lsp.c
+++ b/tools/lsp.c
@@ -173,6 +173,10 @@ main (int argc, char *argv[])
  if (port) {
  printf (" port latency = %" PRIu32 " frames\n",
  jack_port_get_latency (port));
+ printf (" port playback latency = %" PRIu32 " frames\n",
+ jack_port_get_new_latency (port, JackPlaybackLatency));
+ printf (" port capture  latency = %" PRIu32 " frames\n",
+ jack_port_get_new_latency (port, JackCaptureLatency));
  }
  }
  if (show_total_latency) {
--
1.7.2.3

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

[PATCH] [latency api] add default implementation when no latency callback is set

torbenh
In reply to this post by torbenh
---
 libjack/client.c |   52 ++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 52 insertions(+), 0 deletions(-)

diff --git a/libjack/client.c b/libjack/client.c
index adca140..e15f677 100644
--- a/libjack/client.c
+++ b/libjack/client.c
@@ -567,6 +567,7 @@ jack_client_handle_latency_callback (jack_client_t *client, jack_event_t *event)
 {
  jack_latency_callback_mode_t mode = (event->x.n==0) ? JackCaptureLatency : JackPlaybackLatency;
  JSList *node;
+ jack_nframes_t max_latency = 0;
 
  /* first setup all latency values of the ports.
  * this is based on the connections of the ports.
@@ -587,11 +588,62 @@ jack_client_handle_latency_callback (jack_client_t *client, jack_event_t *event)
  * default action is to assume all ports depend on each other.
  * then always take the maximum latency.
  */
+
+ if (mode == JackPlaybackLatency) {
+ /* iterate over all OutputPorts, to find maximum playback latency
+ */
+ for (node = client->ports; node; node = jack_slist_next (node)) {
+ jack_port_t *port = node->data;
+
+ if (port->shared->flags & JackPortIsOutput) {
+ jack_nframes_t port_latency = jack_port_get_new_latency (port, mode);
+ if (port_latency > max_latency)
+ max_latency = port_latency;
+ }
+ }
+
+ /* now set the found latency on all input ports
+ */
+ for (node = client->ports; node; node = jack_slist_next (node)) {
+ jack_port_t *port = node->data;
+
+ if (port->shared->flags & JackPortIsInput) {
+ jack_port_set_new_latency (port, mode, max_latency);
+ }
+ }
+ }
+ if (mode == JackCaptureLatency) {
+ /* iterate over all InputPorts, to find maximum playback latency
+ */
+ for (node = client->ports; node; node = jack_slist_next (node)) {
+ jack_port_t *port = node->data;
+
+ if (port->shared->flags & JackPortIsInput) {
+ jack_nframes_t port_latency = jack_port_get_new_latency (port, mode);
+ if (port_latency > max_latency)
+ max_latency = port_latency;
+ }
+ }
+
+ /* now set the found latency on all output ports
+ */
+ for (node = client->ports; node; node = jack_slist_next (node)) {
+ jack_port_t *port = node->data;
+
+ if (port->shared->flags & JackPortIsOutput) {
+ jack_port_set_new_latency (port, mode, max_latency);
+ }
+ }
+ }
  return 0;
  }
 
+ /* we have a latency callback setup by the client,
+ * lets use it...
+ */
  return client->latency_cb ( mode, client->latency_cb_arg);
 }
+
 #if JACK_USE_MACH_THREADS
 
 static int
--
1.7.2.3

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
In reply to this post by torbenh
On Fri, Jan 07, 2011 at 06:25:52PM +0100, Torben Hohn wrote:

latency api patch...

we dont have a good document on the latency api yet,
there is only this picture:

http://ardour.org/files/jack-latency.png

jack_port_set_new_latency is not a good name, just wanted to get the
code done, to discuss the implementation.

according to paul the old latency api is pretty much wrong, therefore we
should probably just go ahead and deprecate it, instead of trying to
make both apis compatible somehow.


--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Robin Gareus
On 01/07/2011 07:12 PM, torbenh wrote:

> On Fri, Jan 07, 2011 at 06:25:52PM +0100, Torben Hohn wrote:
>
> latency api patch...
>
> we dont have a good document on the latency api yet,
> there is only this picture:
>
> http://ardour.org/files/jack-latency.png
>
> jack_port_set_new_latency is not a good name, just wanted to get the
> code done, to discuss the implementation.
>
> according to paul the old latency api is pretty much wrong, therefore we
> should probably just go ahead and deprecate it, instead of trying to
> make both apis compatible somehow.
>

1+

Many many thanks to get the ball rolling on this one!! It's been overdue
since years :)

I'm just skimming over the code.

In jack_client_handle_latency_callback() would you not need to first
calculate _all_ playback/downstream latencies and only after that is
completed go ahead and calculate the capture/upstream latencies?!

I do not fully comprehend the graph sorting, and it may be that the
current implementation yields the same results because client->ports is
sorted somehow, but since jack_client_handle_latency_callback() can
modify the max_port_latency for both playback and capture ports it looks
as if the computation needs to be serialized (first calc. all playback,
then all capture latencies).

2c,
robin


--
Robin Gareus
web: http://gareus.org/                mail: [hidden email]
lab: http://citu.fr/                   chat: xmpp:[hidden email]

Public Key at http://pgp.mit.edu/  http://gareus.org/public.asc
Fingerprint : 7107 840B 4DC9 C948 076D 6359 7955 24F1 4F95 2B42
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Paul Davis
On Fri, Jan 7, 2011 at 1:43 PM, Robin Gareus <[hidden email]> wrote:

> In jack_client_handle_latency_callback() would you not need to first
> calculate _all_ playback/downstream latencies and only after that is
> completed go ahead and calculate the capture/upstream latencies?!

the server takes care of this. the playback + capture latencies for
each port are NOT connected to each other (see the diagram). in afew
minutes i'll post comments/descriptions for the functions that will
hopefull make this clear.
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Paul Davis
here are some first rough drafts of the documentation for the 3 key
visible functions:

(unknown location)

/**
 * all JACK ports have two latency values associated with them:
 *
 * capture_latency: how long (in frames) since the signal
 *                  delivered to this port arrived at at
 *                  a port marked with JackPortIsTerminal
 *
 * playback_latency: how long (in frames) until the signal
 *                   read from this port will reach a port
 *                   marked with JackPortIsTerminal.
 *
 * Both values might potentially have more than one answer
 * because there may be multiple pathways to/from the port
 * and a terminal port. However, only the smallest one is
 * (should be) stored with the port.
 *
 */

jack_port_get_new_latency ()

/**
 * return the latency defined by @param mode for @param port,
 * in frames.
 *
 * See comments for @function jack_port_???? for the
 * definition of each latency value.
 */

jack_port_set_new_latency ()

/**
 * set the latency defined by @param mode for @param port,
 * in frames.
 *
 * See comments for @function jack_port_???? for the
 * definition of each latency value.
 *
 * This function should ONLY be used inside a latency
 * callback. The client should determine the current
 * value of the latency using @function jack_port_get_new_latency()
 * (called using the same mode as @param mode)
 * and then add some number of frames to that reflects
 * latency added by the client.
 *
 * How much latency a client adds will vary
 * dramatically. For most clients, the answer is zero
 * and there is no reason for them to register a latency
 * callback and thus they should never call this
 * function.
 *
 * More complex clients that take an input signal,
 * transform it in some way and output the result but
 * not during the same process() callback will
 * generally know a single constant value to add
 * to the value returned by @function jack_port_get_new_latency().
 * For example, a client that performed fourier analysis
 * on the incoming signal and removed a certain frequency
 * range from that signal would delay the signal by
 * a certain fixed amount (related to the size of the FFT
 * window used). It would call:
 *
 *   jack_port_set_new_latency (port,
 *      jack_port_get_new_latency (port, @param mode) + delay);
 *
 * Much more complex clients, with complicated data
 * paths and variable latency, are assumed to be written
 * by people who understand this sort of thing.
 */


jack_set_latency_callback ()

/**
 * Tell the Jack server to call @a latency_callback whenever it
 * is necessary to recompute the latencies for some or all
 * Jack ports.
 *
 * @a latency_callback will be called twice each time it is
 * needed, once being passed JackCaptureLatency and once
 * JackPlaybackLatency. See the description of ???? for
 * the definition of each type of latency.
 *
 * ********** IMPORTANT ***********************************
 * Most JACK clients do NOT need to register a latency
 * callback.
 **********************************************************
 *
 * Clients that meet any of the following conditions do NOT
 * need to register a latency callback:
 *
 *    * have only input ports
 *    * have only output ports
 *    * their output is totally unrelated to their input
 *    * their output is not delayed relative to their input
 *        (i.e. data that arrives in a given process()
 *         callback is processed and output again in the
 *         same callback)
 *
 * Clients NOT registering a latency callback MUST also
 * satisfy this condition:
 *
 *    * have no multiple distinct internal signal pathways
 *
 * This means that if your client has more than 1 input and
 * output port, and considers them always "correlated"
 * (e.g. as a stereo pair), then there is only 1 (e.g. stereo)
 * signal pathway through the client. This would be true,
 * for example, of a stereo FX rack client that has a
 * left/right input pair and a left/right output pair.
 *
 * However, this is somewhat a matter of perspective. The
 * same FX rack client could be connected so that its
 * two input ports were connected to entirely separate
 * sources. Under these conditions, the fact that the client
 * does not register a latency callback MAY result
 * in port latency values being incorrect.
 *
 * Clients that do not meet any of those conditions SHOULD
 * register a latency callback. Within that callback, they
 * should call @f jack_port_set_new_latency() for every
 * port they have registered. See the documentation for
 * that function on how to call it. Remember that the @a mode
 * argument given to the latency callback will need to be
 * passed into @f jack_port_set_new_latency()
 */
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
In reply to this post by Robin Gareus
On Fri, Jan 07, 2011 at 07:43:48PM +0100, Robin Gareus wrote:

> On 01/07/2011 07:12 PM, torbenh wrote:
> > On Fri, Jan 07, 2011 at 06:25:52PM +0100, Torben Hohn wrote:
> >
> > latency api patch...
> >
> > we dont have a good document on the latency api yet,
> > there is only this picture:
> >
> > http://ardour.org/files/jack-latency.png
> >
> > jack_port_set_new_latency is not a good name, just wanted to get the
> > code done, to discuss the implementation.
> >
> > according to paul the old latency api is pretty much wrong, therefore we
> > should probably just go ahead and deprecate it, instead of trying to
> > make both apis compatible somehow.
> >
>
> 1+
>
> Many many thanks to get the ball rolling on this one!! It's been overdue
> since years :)
>
> I'm just skimming over the code.
>
> In jack_client_handle_latency_callback() would you not need to first
> calculate _all_ playback/downstream latencies and only after that is
> completed go ahead and calculate the capture/upstream latencies?!

capture and playback latencies are independent of each other.
but they promote in different directions.

thats why capture latency cb is invoked in graph order.
while invoking them i build up a reverse order list.
and then invoke the playback latency callbacks on the reverse order
list.

>
> I do not fully comprehend the graph sorting, and it may be that the
> current implementation yields the same results because client->ports is
> sorted somehow, but since jack_client_handle_latency_callback() can
> modify the max_port_latency for both playback and capture ports it looks
> as if the computation needs to be serialized (first calc. all playback,
> then all capture latencies).

hmm... i think your understanding something wrong.
ports are not sorted in any way. only engine->clients is sorted in graph
order.


>
> 2c,
> robin
>
>
> --
> Robin Gareus
> web: http://gareus.org/                mail: [hidden email]
> lab: http://citu.fr/                   chat: xmpp:[hidden email]
>
> Public Key at http://pgp.mit.edu/  http://gareus.org/public.asc
> Fingerprint : 7107 840B 4DC9 C948 076D 6359 7955 24F1 4F95 2B42

--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Fons Adriaensen-2
In reply to this post by Paul Davis
On Fri, Jan 07, 2011 at 01:57:28PM -0500, Paul Davis wrote:

>  * Both values might potentially have more than one answer
>  * because there may be multiple pathways to/from the port
>  * and a terminal port. However, only the smallest one is
>  * (should be) stored with the port.

With little more effort and code it should be possible to
provide both min and max.

Ciao,

--
FA

There are three of them, and Alleline.

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Paul Davis
On Fri, Jan 7, 2011 at 2:47 PM,  <[hidden email]> wrote:
> On Fri, Jan 07, 2011 at 01:57:28PM -0500, Paul Davis wrote:
>
>>  * Both values might potentially have more than one answer
>>  * because there may be multiple pathways to/from the port
>>  * and a terminal port. However, only the smallest one is
>>  * (should be) stored with the port.
>
> With little more effort and code it should be possible to
> provide both min and max.

what's the use-case justification? cycles are already problematic when
computing this sort of thing, and i admit that i can't see much of
useful reason to know both values - if there are multiple pathways
from A to B then there is quite a bit of other stuff that likely won't
be accurate in some way.
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
In reply to this post by Paul Davis
On Fri, Jan 07, 2011 at 01:57:28PM -0500, Paul Davis wrote:

> here are some first rough drafts of the documentation for the 3 key
> visible functions:
>
> (unknown location)
>
> /**
>  * all JACK ports have two latency values associated with them:
>  *
>  * capture_latency: how long (in frames) since the signal
>  *                  delivered to this port arrived at at
>  *                  a port marked with JackPortIsTerminal
>  *
>  * playback_latency: how long (in frames) until the signal
>  *                   read from this port will reach a port
>  *                   marked with JackPortIsTerminal.
>  *
>  * Both values might potentially have more than one answer
>  * because there may be multiple pathways to/from the port
>  * and a terminal port. However, only the smallest one is
>  * (should be) stored with the port.

the smallest one ?
for connections the code sets the biggest number.
why should a client then set the smallest number ?

either the code is wrong, or this comment, i think.

using fonss min/max proposal, we might be able to avoid discussion on
this point. but its still unclear to me, what a differing min/max value
means. (except a latency error, if someone cares for latency)

if we have:

      B
   /     \
A <        > out  
   \     /
      C

and B and C have a different latency.
it would be an error.

the only fix would be that C would increase latency so that it matches
B. in a DAW this would definitely be the daws job.
its probably not jacks job.

not sure if we should put this burden onto clients though. because every
simple client would need to be able to do it then.

>  *
>  */
>
> jack_port_get_new_latency ()
>
> /**
>  * return the latency defined by @param mode for @param port,
>  * in frames.
>  *
>  * See comments for @function jack_port_???? for the
>  * definition of each latency value.
>  */
>
> jack_port_set_new_latency ()
>
> /**
>  * set the latency defined by @param mode for @param port,
>  * in frames.
>  *
>  * See comments for @function jack_port_???? for the
>  * definition of each latency value.
>  *
>  * This function should ONLY be used inside a latency
>  * callback. The client should determine the current
>  * value of the latency using @function jack_port_get_new_latency()
>  * (called using the same mode as @param mode)
>  * and then add some number of frames to that reflects
>  * latency added by the client.
>  *
>  * How much latency a client adds will vary
>  * dramatically. For most clients, the answer is zero
>  * and there is no reason for them to register a latency
>  * callback and thus they should never call this
>  * function.
>  *
>  * More complex clients that take an input signal,
>  * transform it in some way and output the result but
>  * not during the same process() callback will
>  * generally know a single constant value to add
>  * to the value returned by @function jack_port_get_new_latency().
>  * For example, a client that performed fourier analysis
>  * on the incoming signal and removed a certain frequency
>  * range from that signal would delay the signal by
>  * a certain fixed amount (related to the size of the FFT
>  * window used). It would call:
>  *
>  *   jack_port_set_new_latency (port,
>  *      jack_port_get_new_latency (port, @param mode) + delay);

this is wrong ^^^

if (mode == CaptureLatency)
        jack_port_set_new_latency (output_port,
           jack_port_get_new_latency (input_port, @param mode) + delay);
else
        jack_port_set_new_latency (input_port,
           jack_port_get_new_latency (output_port, @param mode) + delay);


>  *
>  * Much more complex clients, with complicated data
>  * paths and variable latency, are assumed to be written
>  * by people who understand this sort of thing.
>  */
>
>
> jack_set_latency_callback ()
>
> /**
>  * Tell the Jack server to call @a latency_callback whenever it
>  * is necessary to recompute the latencies for some or all
>  * Jack ports.
>  *
>  * @a latency_callback will be called twice each time it is
>  * needed, once being passed JackCaptureLatency and once
>  * JackPlaybackLatency. See the description of ???? for
>  * the definition of each type of latency.
>  *
>  * ********** IMPORTANT ***********************************
>  * Most JACK clients do NOT need to register a latency
>  * callback.
>  **********************************************************
>  *
>  * Clients that meet any of the following conditions do NOT
>  * need to register a latency callback:
>  *
>  *    * have only input ports
>  *    * have only output ports
>  *    * their output is totally unrelated to their input
>  *    * their output is not delayed relative to their input
>  *        (i.e. data that arrives in a given process()
>  *         callback is processed and output again in the
>  *         same callback)
>  *
>  * Clients NOT registering a latency callback MUST also
>  * satisfy this condition:
>  *
>  *    * have no multiple distinct internal signal pathways
>  *
>  * This means that if your client has more than 1 input and
>  * output port, and considers them always "correlated"
>  * (e.g. as a stereo pair), then there is only 1 (e.g. stereo)
>  * signal pathway through the client. This would be true,
>  * for example, of a stereo FX rack client that has a
>  * left/right input pair and a left/right output pair.
>  *
>  * However, this is somewhat a matter of perspective. The
>  * same FX rack client could be connected so that its
>  * two input ports were connected to entirely separate
>  * sources. Under these conditions, the fact that the client
>  * does not register a latency callback MAY result
>  * in port latency values being incorrect.
>  *
>  * Clients that do not meet any of those conditions SHOULD
>  * register a latency callback. Within that callback, they
>  * should call @f jack_port_set_new_latency() for every
>  * port they have registered. See the documentation for

for mode == CaptureLatency they need to call it on every output port.
and otherwise for every input port.

>  * that function on how to call it. Remember that the @a mode
>  * argument given to the latency callback will need to be
>  * passed into @f jack_port_set_new_latency()
>  */
> _______________________________________________
> Jack-Devel mailing list
> [hidden email]
> http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org

--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
In reply to this post by Paul Davis
On Fri, Jan 07, 2011 at 03:18:41PM -0500, Paul Davis wrote:

> On Fri, Jan 7, 2011 at 2:47 PM,  <[hidden email]> wrote:
> > On Fri, Jan 07, 2011 at 01:57:28PM -0500, Paul Davis wrote:
> >
> >>  * Both values might potentially have more than one answer
> >>  * because there may be multiple pathways to/from the port
> >>  * and a terminal port. However, only the smallest one is
> >>  * (should be) stored with the port.
> >
> > With little more effort and code it should be possible to
> > provide both min and max.
>
> what's the use-case justification? cycles are already problematic when
> computing this sort of thing, and i admit that i can't see much of
> useful reason to know both values - if there are multiple pathways
> from A to B then there is quite a bit of other stuff that likely won't
> be accurate in some way.

as i stated in another mail.
the only reson i see, is that if someone reallt cares for latency being
correct, its an error if min and max are different.

--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Paul Davis
In reply to this post by torbenh
On Fri, Jan 7, 2011 at 3:33 PM, torbenh <[hidden email]> wrote:

>>  * Both values might potentially have more than one answer
>>  * because there may be multiple pathways to/from the port
>>  * and a terminal port. However, only the smallest one is
>>  * (should be) stored with the port.
>
> the smallest one ?
> for connections the code sets the biggest number.
> why should a client then set the smallest number ?
>
> either the code is wrong, or this comment, i think.

just tell me which :)

> this is wrong ^^^
>
> if (mode == CaptureLatency)
>        jack_port_set_new_latency (output_port,
>           jack_port_get_new_latency (input_port, @param mode) + delay);
> else
>        jack_port_set_new_latency (input_port,
>           jack_port_get_new_latency (output_port, @param mode) + delay);

will fix.


> for mode == CaptureLatency they need to call it on every output port.
> and otherwise for every input port.

will fix.
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
On Fri, Jan 07, 2011 at 03:39:59PM -0500, Paul Davis wrote:

> On Fri, Jan 7, 2011 at 3:33 PM, torbenh <[hidden email]> wrote:
>
> >>  * Both values might potentially have more than one answer
> >>  * because there may be multiple pathways to/from the port
> >>  * and a terminal port. However, only the smallest one is
> >>  * (should be) stored with the port.
> >
> > the smallest one ?
> > for connections the code sets the biggest number.
> > why should a client then set the smallest number ?
> >
> > either the code is wrong, or this comment, i think.
>
> just tell me which :)

thats the big question.
do we use min, or max ?

i actually begin to like fonss min/max proposal.
because then an application is able to hint the user on the latency
errors.

i am curious if this is what fons had in mind.

>
> > this is wrong ^^^
> >
> > if (mode == CaptureLatency)
> >        jack_port_set_new_latency (output_port,
> >           jack_port_get_new_latency (input_port, @param mode) + delay);
> > else
> >        jack_port_set_new_latency (input_port,
> >           jack_port_get_new_latency (output_port, @param mode) + delay);
>
> will fix.
>
>
> > for mode == CaptureLatency they need to call it on every output port.
> > and otherwise for every input port.
>
> will fix.

ok.

> _______________________________________________
> Jack-Devel mailing list
> [hidden email]
> http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org

--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Fons Adriaensen-2
In reply to this post by torbenh
On Fri, Jan 07, 2011 at 09:36:45PM +0100, torbenh wrote:

> as i stated in another mail.
> the only reson i see, is that if someone reallt cares for latency being
> correct, its an error if min and max are different.

And if they are different, I see no reason why min should be preferred
or considered more interesting than max. It depends on the application.
So you need both.

Ciao,

--
FA

There are three of them, and Alleline.

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Arnold Krille-3
In reply to this post by torbenh
On Friday 07 January 2011 21:33:42 torbenh wrote:

> if we have:
>
>       B
>    /     \
> A <        > out
>    \     /
>       C
>
> and B and C have a different latency.
> it would be an error.
>
> the only fix would be that C would increase latency so that it matches
> B. in a DAW this would definitely be the daws job.
> its probably not jacks job.
>
> not sure if we should put this burden onto clients though. because every
> simple client would need to be able to do it then.
Why not implement the fix for this problem at the one position where its
actually fixable: at the clients output-buffers in libjack?
That way no client has to worry about it and all clients immediately benefit
from it. And the actual implementation can be jack-flavour-dependent.

Have fun,

Arnold

_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org

signature.asc (205 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

Paul Davis
On Fri, Jan 7, 2011 at 8:08 PM, Arnold Krille <[hidden email]> wrote:

> On Friday 07 January 2011 21:33:42 torbenh wrote:
>> if we have:
>>
>>       B
>>    /     \
>> A <        > out
>>    \     /
>>       C
>>
>> and B and C have a different latency.
>> it would be an error.
>>
>> the only fix would be that C would increase latency so that it matches
>> B. in a DAW this would definitely be the daws job.
>> its probably not jacks job.
>>
>> not sure if we should put this burden onto clients though. because every
>> simple client would need to be able to do it then.
>
> Why not implement the fix for this problem at the one position where its
> actually fixable: at the clients output-buffers in libjack?
> That way no client has to worry about it and all clients immediately benefit
> from it. And the actual implementation can be jack-flavour-dependent.

i'm not sure what you mean by "a fix for this problem", because i
don't know what you mean by "this problem", but i suspect you mean
"JACK should do latency compensation". its not happening as long as
i'm involved in the project.

it becomes pointless as soon as (a) a client doesn't bother to
correctly report latency (b) a client has its own internal signal flow
pathways that don't go via JACK but can still have latency (c)
requires difficult and context-specific decisions about how to handle
data flow when latency changes (much more difficult, for example, than
just graph changes, because you have delay buffers needing to be reset
(d) prevents applications that can do latency compensation via delayed
playback from doing so, which is much much more efficient than the
buffers that JACK would have to use.

if you meant some other problem, i apologize.
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
In reply to this post by Fons Adriaensen-2
On Sat, Jan 08, 2011 at 01:02:07AM +0100, [hidden email] wrote:
> On Fri, Jan 07, 2011 at 09:36:45PM +0100, torbenh wrote:
>
> > as i stated in another mail.
> > the only reson i see, is that if someone reallt cares for latency being
> > correct, its an error if min and max are different.
>
> And if they are different, I see no reason why min should be preferred
> or considered more interesting than max. It depends on the application.
> So you need both.

i dont see a reason either, that any of the two should be preferred.
however. its absolutely unclear to me, what an application would do,
when it finds out, that a port is connected to a path with a latency
from 1024 to 2048...

you cant compensate for a latency range.
its a user error and he would get phasing.

please provide a use-case. that would be a lot more convincing,
to add the struct latency_range to the api.

--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
Reply | Threaded
Open this post in threaded view
|

Re: [PATCH 1/3] [latency api] first go on latency api

torbenh
In reply to this post by Arnold Krille-3
On Sat, Jan 08, 2011 at 02:08:33AM +0100, Arnold Krille wrote:

> On Friday 07 January 2011 21:33:42 torbenh wrote:
> > if we have:
> >
> >       B
> >    /     \
> > A <        > out
> >    \     /
> >       C
> >
> > and B and C have a different latency.
> > it would be an error.
> >
> > the only fix would be that C would increase latency so that it matches
> > B. in a DAW this would definitely be the daws job.
> > its probably not jacks job.
> >
> > not sure if we should put this burden onto clients though. because every
> > simple client would need to be able to do it then.
>
> Why not implement the fix for this problem at the one position where its
> actually fixable: at the clients output-buffers in libjack?
> That way no client has to worry about it and all clients immediately benefit
> from it. And the actual implementation can be jack-flavour-dependent.

latency compensation using delays is not what we are aiming at.
we want to compensate latency by playing back things earlier.

obviously in a parallel dataflow, we need a delay.
but i am with paul here. jack should not do this implicitly.

maybe we could add another callback, which could request a latency
change on a port ?
this is probably a can of worms.

>
> Have fun,
>
> Arnold



> _______________________________________________
> Jack-Devel mailing list
> [hidden email]
> http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org


--
torben Hohn
_______________________________________________
Jack-Devel mailing list
[hidden email]
http://lists.jackaudio.org/listinfo.cgi/jack-devel-jackaudio.org
12