Make collect_nodes return a list of all nodes that are in some way
linked to the node and need to be scheduled as a group.
Move all the collected nodes to a driver, a fallback driver or away
from a driver.
This fixes some cases where nodes were moved quickly between drivers,
causing a lot of activation messages to be sent and fds to be dupped.
Nodes should now only move when needed with minimal amount of
changes to their state.
See #2309
When the stream requests a 0 size buffer, don't start the drain but
simply queue a 0 size buffer.
Sometimes, switching quantums and drivers might request a 0 buffer
async and this should not cause a drain operation.
When we detect that no new profiler info has arrived for a node, assume
it was removed from the driver.
This avoids having idle nodes seemingly attached to an idle driver
when there is no activity.
We can only call collect_nodes() once because it sets the visited state
to true.
So, move the unassigned nodes to the fallback driver but when they are
passive (nothing is linked), move them back to the NULL driver.
This fixes a case where when the fallback driver changes, only some
nodes are moved to the new driver (because the other ones were already
visited in the collect_nodes() check before).
Track the end-to-end latency of the stream and use that to drive
the resampler.
Hard reset the ringbuffer when under/overflow happens so that we
can recover quickly.
See #2230
Don't move passive nodes to the fallback driver when !always_process.
When we have a fallback driver, check if the node we want to add to it
is not a passive node (by doing collect_nodes), if it's passive and
doesn't always need to be processed, remove it from the driver.
This fixes the issue where nodes that are maked as want_driver are
unconditionally moved to the fallback driver (and activated) even if
there is nothing linked to them (passive).
Fixes#2309
Make helper method to parse thread properties and add 2 new properties
to control name and stack-size of the thread.
Use properties when creating threads with the default utils.
Use the default thread utils instead of pthread_create so that the
properties are used.
When a node is moved from one driver to another, recheck if the new
driver needs a quantum/rate change.
Because the node was running on the old driver, the locked flag was
checked and applied to the new driver, causing the new driver to keep
running with the old (possible wrong) quantum/rate.
Fixes#2293
Increase the FC filter frequency to 12KHz for better dialogs. This
filter is only applied when making the FC from FRONT channels so that
we keep the high frequency signal on the FRONT mostly.
Increase LFE filter frequency to make slightly more bass.
Disable widen filter by default.
Update config files with the correct defaults.
Move all module methods into the `module_info` struct, and place
all such structs into the "pw_mod_pulse_modules" section of
the executable. This way there is no need for an explicit
module registry, and all information about a module can
be declared in the module's source file in a single place.
Exported nodes (streams, filter) are not registered in the local
context and notify the server when they change active state.
When the node becomes inactive, this triggers a message to the server to
make the node inactive, which then eventually results in a PAUSE request
on the node, which then removes the node from the processing loop.
Unfortunately, clients expect that after a node is set inactive, the
process function will not be called anymore and they might free any
resources immediately. Handle this by removing the node from the
data-loop and waiting for completion.
This should fix some crashes when streams are stopped.
Just stop the data-loop before destroying the modules because they might
still try to access it.
Destroy the data-loop in the free phase instead.
Fixes a valgrind error where module-rt tries to clear the thread-utils,
which causes the context to try to clear the thread-utils on the already
freed data-loop.
We use the done event to send the object serial to the client. Use an
invalid object id for this and filter it out on the receiver or else
the client might get an unexpected done event.
Fixes#2253
The RTKit module is being replaced by the RT module. Currently, it is
always built if D-Bus is present. For packagers, it can be beneficial to
be able to disable the legacy module. Add a Meson option to allow for
exactly that. Make it enabled by default to not change default behavior.
Setting a global thread-utils is not a good idea, especially
when multiple contexts will register their own interface.
Instead, set the thread-utils as a context object and use this to
configure the data loop in the context.
In JACK we need a per context implementation of the interface so that
we can find the context specific thread-utils.
See #2252
Assign half the latency to the internal ringbuffer and half on the
network and remote end.
Use a dll to calculate the drift from our target ringbuffer fill
level and use the stream rate property to driver the resampler.
This should reduce uncontrolled latency over the tunnel.
PulseAudio wants us to be a driver will pull requests from the remote
side. We would need to provide a clock based on the remote end and
also try to follow it when we are not a driver. It would be slightly
better because in the normal playback case we would be able to
avoid resampling. We might do this eventually.
The PropInfo either has a registered id (and then also a name from the
type-info) or a custom name as a string.
In all cases, the description contains a free form text that clarifies
the property.
Use the description in the stream controls name.
For the modules that require a driver, don't add ourselves to
the pipewire.dummy group but instead just use the NODE_WANT_DRIVER
property to be assigned to a driver.
This makes it possible for the nodes to move to another driver than the
dummy driver (which has very high priority) and it avoids resampling in
cases where the nodes are linked to an audio source or sink.
Only make the driver node active when we assign it an always_process
node. Otherwise we can keep the driver passive until some other active
nodes are added.
Fixes a case where an need_driver node would automatically activate
the driver, even when nothing is to be scheduled.
Deprecate pw_stream_get_time() in favour of _get_time_n() that contains
the size of the pw_time structure. Make the old one fill in the fields
up to the buffered field. Make the new one use the size to decide how
much info to fill in.
Add a new buffered field in pw_time that contains the buffered data
inside the converter/resampler. This leaves the queued field with
purely the user provided size in the buffers.
Use get_time_n() in places.