Make a real debug context with a log function and move it to a new file.
This way we don't need to redefine a macro.
Make a new context for debugging to a log file. Make new functions to
debug to a log file.
Move the stringbuffer to string utils.
Integrate file/line/func and topics into the debug log.
We can remove some more things from the pipewire log_object function and
also add support for topics.
Add a reconfigure state on the node that is set when the node was IDLE
or RUNNING when reconfigured.
The node state will be set to the running state as long as the
reconfigure state is active. When the node is running, the reconfigure
state is unset again and the node is allowed to IDLE as usual.
This fixes the case where an IDLE (but not paused node) will be
suspended when a rate change happens but will then not resume
afterwards.
This causes problems with rate changes and nodes that have the suspend
disabled by the session manager. They will be suspened anyway and this
can cause problems for devices that need to keep running to keep the
amplifiers active.
Fixes#2929
Add a sequence number to pw_param.
Add param_info to param_update to filter out the params of the latest
sequence number.
This can be used to track params from a certain sequence number. Update
node, port and device.
Only activate the input links to a node after the node has been added to
the graph.
This ensure that we don't accidentaly schedule the node before the Start
command has completed and the node is actually ready to process data.
The Start command might be async and we should not schedule the node
until the reply has arrived and we have actually added the node to
the graph.
Otherwise it is possible that the node is scheduled before it could
complete the start command. This could be a problem for adapter because
it does negotiation and so on in the Start call.
See #2677
Add a refcount to resource and client so that we can keep them alive
while the native protocol is using them.
One problem might be that the protocol destroys the client or resource
while handling it and that would cause errors.
Fixes#565
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
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
Not all clients have an existing registry, and the registry generation
number will not be updated for them. However, we would like to check
for stale globals also elsewhere, eg. metadata, and it must work also
in this case.
To avoid failing to update client registry generation, on global
addition which the client would see if it had a registry, send done
message for the new global id instead.
Some client messages have bare ids (as opposed to proxies/resources),
eg. as in pw_registry_bind/destroy. If the client is processing
messages late, these may refer to an object that was already removed,
and the id may now refers to a differnt objects. I.e. the following
race condition needs to be resolved:
server client
Global 1 (gen. 1)
Global 1
Global 1 remove
Global 1 (gen. 2)
Bind/destroy 1
Where the client would bind/destroy the wrong global, since it did not
yet see the messages for the second one.
To keep track of which object the client means, the server keeps track of
the "generation number" of its global registry, and what generation
the client is at.
Each global remembers at what generation of registry they were
registered. When processing the messages that use bare ids, check the
registry generation of the client, to know whether the message refers to
a stale global that was already removed.
Messages where client sends bare ids to server are:
pw_registry_bind, pw_registry_destroy, metadata_set_property
In pw_registry_* do the staleness check directly. Also add staleness
check in pw_impl_client_check_permissions, so that also the metadata
case is handled.
The generation numbers are passed around in message footers, but only if
they have changed. When the generation number changes on server, we
send the updated value to the client in a message footer. When client
has received an update value, it will send the value back in the footer
of the next message it sends to the server.
Based on: Wim Taymans <wtaymans@redhat.com> "impl-core: check serial number"
Add `pw_impl_module_schedule_destroy()` which will
schedule a call to `pw_impl_module_destroy()` on
the module's context's work queue.
For now, do not add it to the public impl-module.h header,
only private.h.
Add a node.force-quantum and node.force-rate property. When no global
quantum or rate is enforce with settings, the last updated node property
is used as the quantum.
Make jack use the force-quantum property when set_buffersize is used to
make sure that the quantum is not just a suggestion but a hard forced
one. This makes it possible for ardour or other jack apps to raise the
quantum above the max-quantum but also ensure that it will not change
by any other application (unless other jack apps).
Fixes#2079
Add an option to check if the rate and quantum configured with the
settings metadata is in the allowed range.
This is false by default, you can use metadata to set any rate/quantum
but in a minimal controlled setup you might want to restrict this.
Store the globals by id in a hashtable. O(1) insert and remove.
It moves the find_global overhead from the top of the list to somewhere
in the middle for the jack-stress test.
Keep a sorted circular list of the globals by id. Keep all globals
smaller than the current serial at the tail and the globals bigger in
the front. When we wrap around we will eventually have a collision with
the head global, we can then skip that id, move the global to the tail
and try the next id.
In the normal case, this is O(1) collision check and O(1) removal. In
the case of a collisions, it needs to skip the cluster of used ids.
See !1108
Add the global immediately after creating it. Make sure we only
enumerate registered globals. This way, we can already check for
duplicate ids before the global is registered.
When allocating a global id, avoid using an existing id. Move some
code around to make it easier to implement a more efficient algorithm
for collision detection.
Move the object id counter to the context.
Make it possible to change the quantum-limit in the config file past
8192 up to 65536. This will make all plugins allocate larger buffers
so that the quantum can be increased to larger values as well,
This is interesting when dealing with higher sample rates where the
8192 sample limit will cause wakeups every 20ms at 384KHz.
See #1931
Also scale the max_quantum with the selected rate. Add a new
quantum_limit property that is the upper limit of the quantum regardless
of the sample rate, this is usually the allocated buffer size.
See #1931
Only update the quantum/rate when we have a pending change.
This works around a bug in sco-source that changes the quantum
by itself but in any case, this optimization is nice to have.
See #1905
Don't directly update the quantum and rate in the driver position
when recalculating the graph or else clients might see different values
during one cycle.
Instead update another variable and copy this into the position when
we start a new cycle.
pw_log_log/logv now go through the topic-based logger using the
"default" topic. Log topics themselves can be allocated by the call
sites. The simplest way to use a topic from e.g. a module:
PW_LOG_TOPIC_STATIC(mod_topic, "mod.foo");
#define PW_LOG_TOPIC_DEFAULT mod_topic
...
void pipewire__module_init() {
PW_LOG_TOPIC_INIT(mod_topic);
...
}
With the #define all pw_log_foo() are now routed through the custom
topic. For the cases where the log topic must be specified, a
pw_logt_foo() set of macros is available.
Log topics are enabled through the PIPEWIRE_DEBUG environment variable
which now supports globs, e.g. PIPEWIRE_DEBUG="*:I;mod.access:D"
to enable global INFO but DEBUG for the access module.
Namespaces documented are "pw", "mod" and "conn", for pipewire-internal
stuff, modules and connection dumping. The latter is special-cased to
avoid spamming the log files, it requires an expcit "conn.<glob>"
pattern to enable.
The "default" topic always exists and is the fallback for any
pw_log_foo() invocation that does not use a topic.
When the node support transport sync. That is, when it will clear the
pending_sync flag from its activation area when it completed a new
seek.
Before this patch, the pending sync was always automatically cleared,
which broke some applications that are time masters such as bitwig.
Fixes#1589
When multiple links are created at the same time for the same port, we
get into a race where multiple links will try to set a format
asynchronously and eventually break the links. Avoid this by marking the
port as busy for as long as an async format or buffer is pending and
avoid starting new link negotiation when one of the ports is busy.
This problem was observed when ardour6 tries to link all device capture
ports to its single monitor port.
If a log message is rate limited, we only need to know about it if we
are actually interested in that log level. We therefore add an argument
to the ratelimit_test function to set the log level of the message
printed if a message is skipped
Change-Id: I5ccd4a78bf7e972fe8b0e7133cd7e08c1e38835f
Add a default.clock.allowed-rates property that lists the possible
rates for the graph.
Add node.rate and node.lock-rate properties to suggest a graph rate
and lock the rate.
Collect the largest clock rate from the nodes and if it is allowed,
try to configure it as the graph rate. Only switch rates when the
driver is IDLE or suspended or when we force a rate.
No alternative samplerates are specified because we first need to
work around a common driver bug (cards with 1 cristal need the same
rate for capture as playback) for this to work.
Rework the quantum and max_quantum handling. Work directly with the
latency fractions and calculate the final quantum size until we know
the samplerate.