We should not use nsec from the clock as the current_usec because
current_usec is supposed to be an idealized time when the wakeup would
have happened and nsec is when it actually happened.
Instead use next_nsec and subtract the rate corrected period from it to
get the idealized current_usec.
We can still use nsec to calculate the elapsed time since the wakeup and
be sure that it is always in the past.
Some JACK clients place OSC messages in MIDI buffers. Try to detect the
OSC messages and mark the control as OSC.
Also allow OSC control to be converted to JACK MIDI.
This should make things work better with native PipeWire clients that
handle MIDI and OSC.
Ardour calls jack_port_get_buffer() from multiple threads. For audio
buffers this will result in mixing the input samples into the target
buffer and there is no window for having a corrupt buffer.
For MIDI, there is a problem because we need to convert from and to
PipeWire MIDI and while we do that from multiple threads, the midi
buffer can be incomplete or corrupt.
Fix this by building the intermediate POD to a thread-local scratch area
and then copy it to the target buffer. If this is done from multiple
threads there is no moment where incomplete data can be seen in the
target buffer.
Make the complete midi-scratch buffer thread_local so that we also avoid
a race when converting midi data from a foreign port.
When we write into the scratch buffer when mixing and converting input
midi data, we also avoid a race there.
Fixes#3632
Avoid reading from the activation directly to get cycle times but copy
the relevant fields of the clock when the cycle starts. Use the unique id
to get a consistent copy of the data.
This avoids some stay frames and values in jack_showtime.
Improve get_buffer debug.
Add some extra checks for the type before we try to use the object as a
port.
Set latency range to 0 when called with wrong port. Ardour seems to call
into us with ports from a previous jack_client..
When we get a midi buffer directly from one of our peer ports, we need
to convert it to a jack midi buffer.
Note that this previously returned NULL because of the size check of the
midi buffer, which was likely much smaller than the frames argument.
This fixes midi event recording preview in ardour.
PW_VERSION_NODE is 3 while PW_VERSION_NODE_EVENTS is 0, I am unsure if
it could have caused issues. Same thing with PW_VERSION_PORT &
PW_VERSION_PORT_EVENTS.
I have not seen code checking this version number.
Signed-off-by: Théo Lebrun <theo.lebrun@bootlin.com>
do a sync when starting up client and sync when creating a new proxy so
that we get all the proxy updates before the client is opened.
This ensures all ports are enumerated correctly.
Fixes#3618
Don't set the port io to NEED_DATA in prepare_output because this
might be called when we get the data from an input port that is linked
to out output port.
See #3514
We can directly use the port io, which is always available. This ensures
the mix->io status is set to NEED_DATA even when there is no global
mix.
This reverts part of 56786aedc4
See #3514
Some jack clients will take a lock before doing IPC and then will
take the same lock in a notify callback. This prevents the IPC from
progressing and causes a deadlock.
Make a separate thread to dispatch the notify so that we don't block the
IPC in any case.
Fixes#3585
Some jack clients like to lock the process function and so we can't be
sure we will deadlock while we try to wait for the data-loop.
Instead, don't sync with the data-loop when setting the mix-io, it will
happen later when it is possible. Queue a free operation of the memmap
after the mix_set_io if we need to clean up.
See #3585
This reverts commit 6fefd49a8a.
We can't use PRIVATE because mmap docs say that we then might not see
changes in the data anymore from other processes.
Fixes#3575
Do a do_sync after setting the metadata to ensure the messages are
flushed to the server and processed. Fixes an issue where jack_property
would exit before the messages are flushed and so nothing happens.
Change the shellcheck job so that we configure the build and check the
preprocessed versions of the scripts, not the bare ones, which might not
be syntactically valid yet.
The buffer io area is used to enable/disable a port and should be
synchronized with the processing loop. Use invoke to safely update the
mixer io area.
Keep track of the number of mixers on a port and clear the global mixer
buffer io when there are none. Check and use the global mixer io when
processing output to avoid using an inactive output without buffers and
crashing.
Fixes#3506
When we activate, emit the port registration events of our own port,
even when they were suppressed (and marked registered) when we created
them. This is what JACK2 does as well.
When we don't manage to emit the notify, still mark the object as
registered. Otherwise we might not emit the unregistered
notify later on.
This usually happens when a client connects and the notifies are
suppressed for all the objects in the graph. When they later disappear
we do want to emit the unregistered notify.
We can't really do zero copy because our downstream peer does not have
access to the memfd of our upstream peer. Instead, just memcpy the
data for now.
When the buffer frames change, make sure we emit a latency recalculation
even if we don't have a buffer_size callback.
Remove the unused GRAPH notify.
Protect ringbuffer writes to the notify queue with a lock because we
can't know what thread they execute in.
Make a new TOTAL_LATENCY notify type to trigger a complete latency
recalculation.
Node that have the node.always-process = false property do not conform
to the jack API because they will be suspended even when they don't
inactivate themselves. Don't hide the ports for those clients when
inactive.
Fixes#3416
The jack client API expects the ports to unregister when a jack client is
deactivated and to register when it is activated. We use pause/resume
for deactivate/activate and don't really destroy the ports.
Track the state of the node (client) and emit port registration when it
changes state. Also make sure we don't emit a port registration when the
node is deactivated.
Fixes#3260