| /* PipeWire */ | |
| /* SPDX-FileCopyrightText: Copyright © 2018 Wim Taymans */ | |
| /* SPDX-License-Identifier: MIT */ | |
| #ifndef PIPEWIRE_STREAM_H | |
| #define PIPEWIRE_STREAM_H | |
| #ifdef __cplusplus | |
| extern "C" { | |
| #endif | |
| /** \page page_streams Streams | |
| * | |
| * \see \ref pw_stream | |
| * | |
| * \section sec_overview Overview | |
| * | |
| * \ref pw_stream "Streams" are used to exchange data with the | |
| * PipeWire server. A stream is a wrapper around a proxy for a pw_client_node | |
| * with an adapter. This means the stream will automatically do conversion | |
| * to the type required by the server. | |
| * | |
| * Streams can be used to: | |
| * | |
| * \li Consume a stream from PipeWire. This is a PW_DIRECTION_INPUT stream. | |
| * \li Produce a stream to PipeWire. This is a PW_DIRECTION_OUTPUT stream | |
| * | |
| * You can connect the stream port to a specific server port or let PipeWire | |
| * choose a port for you. | |
| * | |
| * For more complicated nodes such as filters or ports with multiple | |
| * inputs and/or outputs you will need to use the pw_filter or make | |
| * a pw_node yourself and export it with \ref pw_core_export. | |
| * | |
| * Streams can also be used to: | |
| * | |
| * \li Implement a Sink in PipeWire. This is a PW_DIRECTION_INPUT stream. | |
| * \li Implement a Source in PipeWire. This is a PW_DIRECTION_OUTPUT stream | |
| * | |
| * In this case, the PW_KEY_MEDIA_CLASS property needs to be set to | |
| * "Audio/Sink" or "Audio/Source" respectively. | |
| * | |
| * \section sec_create Create | |
| * | |
| * Make a new stream with \ref pw_stream_new(). You will need to specify | |
| * a name for the stream and extra properties. The basic set of properties | |
| * each stream must provide is filled in automatically. | |
| * | |
| * Once the stream is created, the state_changed event should be used to | |
| * track the state of the stream. | |
| * | |
| * \section sec_connect Connect | |
| * | |
| * The stream is initially unconnected. To connect the stream, use | |
| * \ref pw_stream_connect(). Pass the desired direction as an argument. | |
| * | |
| * The direction is: | |
| * \li PW_DIRECTION_INPUT for a stream that *consumes* data. This can be a | |
| * stream that captures from a Source or a when the stream is used to | |
| * implement a Sink. An application will use a \ref PW_DIRECTION_INPUT | |
| * stream to record data. A virtual sound card will use a | |
| * \ref PW_DIRECTION_INPUT stream to implement audio playback. | |
| * | |
| * \li PW_DIRECTION_OUTPUT for a stream that *produces* data. This can be a | |
| * stream that plays to a Sink or when the stream is used to implement | |
| * a Source. An application will use a \ref PW_DIRECTION_OUTPUT | |
| * stream to produce data. A virtual sound card or camera will use a | |
| * \ref PW_DIRECTION_OUTPUT stream to implement audio or video recording. | |
| * | |
| * \subsection ssec_stream_target Stream target | |
| * | |
| * To make the newly connected stream automatically connect to an existing | |
| * PipeWire node, use the \ref PW_STREAM_FLAG_AUTOCONNECT and set the | |
| * PW_KEY_OBJECT_SERIAL or the PW_KEY_NODE_NAME value of the target node | |
| * in the PW_KEY_TARGET_OBJECT property before connecting. | |
| * | |
| * \subsection ssec_stream_formats Stream formats | |
| * | |
| * An array of possible formats that this stream can consume or provide | |
| * must be specified. | |
| * | |
| * \section sec_format Format negotiation | |
| * | |
| * After connecting the stream, the server will want to configure some | |
| * parameters on the stream. You will be notified of these changes | |
| * with the param_changed event. | |
| * | |
| * When a format param change is emitted, the client should now prepare | |
| * itself to deal with the format and complete the negotiation procedure | |
| * with a call to \ref pw_stream_update_params(). | |
| * | |
| * As arguments to \ref pw_stream_update_params() an array of spa_param | |
| * structures must be given. They contain parameters such as buffer size, | |
| * number of buffers, required metadata and other parameters for the | |
| * media buffers. | |
| * | |
| * \section sec_buffers Buffer negotiation | |
| * | |
| * After completing the format negotiation, PipeWire will allocate and | |
| * notify the stream of the buffers that will be used to exchange data | |
| * between client and server. | |
| * | |
| * With the add_buffer event, a stream will be notified of a new buffer | |
| * that can be used for data transport. You can attach user_data to these | |
| * buffers. The buffers can only be used with the stream that emitted | |
| * the add_buffer event. | |
| * | |
| * After the buffers are negotiated, the stream will transition to the | |
| * \ref PW_STREAM_STATE_PAUSED state. | |
| * | |
| * \section sec_streaming Streaming | |
| * | |
| * From the \ref PW_STREAM_STATE_PAUSED state, the stream can be set to | |
| * the \ref PW_STREAM_STATE_STREAMING state by the PipeWire server when | |
| * data transport is started. | |
| * | |
| * Depending on how the stream was connected it will need to Produce or | |
| * Consume data for/from PipeWire as explained in the following | |
| * subsections. | |
| * | |
| * \subsection ssec_consume Consume data | |
| * | |
| * The process event is emitted for each new buffer that can be | |
| * consumed. | |
| * | |
| * \ref pw_stream_dequeue_buffer() should be used to get the data and | |
| * metadata of the buffer. | |
| * | |
| * The buffer is owned by the stream and stays alive until the | |
| * remove_buffer callback has returned or the stream is destroyed. | |
| * | |
| * When the buffer has been processed, call \ref pw_stream_queue_buffer() | |
| * to let PipeWire reuse the buffer. | |
| * | |
| * Although not strictly required, it is recommended to call \ref | |
| * pw_stream_dequeue_buffer() and pw_stream_queue_buffer() from the | |
| * process() callback to minimize the amount of buffering and | |
| * maximize the amount of buffer reuse in the stream. | |
| * | |
| * It is also possible to dequeue the buffer from the process event, | |
| * then process and queue the buffer from a helper thread. It is also | |
| * possible to dequeue, process and queue a buffer from a helper thread | |
| * after receiving the process event. | |
| * | |
| * \subsection ssec_produce Produce data | |
| * | |
| * The process event is emitted when a new buffer should be queued. | |
| * | |
| * When the PW_STREAM_FLAG_RT_PROCESS flag was given, this function will be | |
| * called from a realtime thread and it is not safe to call non-reatime | |
| * functions such as doing file operations, blocking operations or any of | |
| * the PipeWire functions that are not explicitly marked as being RT safe. | |
| * | |
| * \ref pw_stream_dequeue_buffer() gives an empty buffer that can be filled. | |
| * | |
| * The buffer is owned by the stream and stays alive until the | |
| * remove_buffer event is emitted or the stream is destroyed. | |
| * | |
| * Filled buffers should be queued with \ref pw_stream_queue_buffer(). | |
| * | |
| * Although not strictly required, it is recommended to call \ref | |
| * pw_stream_dequeue_buffer() and pw_stream_queue_buffer() from the | |
| * process() callback to minimize the amount of buffering and | |
| * maximize the amount of buffer reuse in the stream. | |
| * | |
| * Buffers that are queued after the process event completes will be delayed | |
| * to the next processing cycle. | |
| * | |
| * \section sec_stream_driving Driving the graph | |
| * | |
| * Starting in 0.3.34, it is possible for a stream to drive the graph. | |
| * This allows interrupt-driven scheduling for drivers implemented as | |
| * PipeWire streams, without having to reimplement the stream as a SPA | |
| * plugin. | |
| * | |
| * A stream cannot drive the graph unless it is in the | |
| * \ref PW_STREAM_STATE_STREAMING state and \ref pw_stream_is_driving() returns | |
| * true. It must then use pw_stream_trigger_process() to start the graph | |
| * cycle. | |
| * | |
| * \ref pw_stream_trigger_process() will result in a process event, where a buffer | |
| * should be dequeued, and queued again. This is the recommended behaviour that | |
| * minimizes buffering and maximized buffer reuse. | |
| * | |
| * Producers of data that drive the graph can also dequeue a buffer in a helper | |
| * thread, fill it with data and then call \ref pw_stream_trigger_process() to | |
| * start the graph cycle. In the process event they will then queue the filled | |
| * buffer and dequeue a new empty buffer to fill again in the helper thread, | |
| * | |
| * Consumers of data that drive the graph (pull based scheduling) will use | |
| * \ref pw_stream_trigger_process() to start the graph and will dequeue, process | |
| * and queue the buffers in the process event. | |
| * | |
| * \section sec_stream_process_requests Request processing | |
| * | |
| * A stream that is not driving the graph can request a new graph cycle by doing | |
| * \ref pw_stream_trigger_process(). This will result in a RequestProcess command | |
| * in the driver stream. If the driver supports this, it can then perform | |
| * \ref pw_stream_trigger_process() to start the actual graph cycle. | |
| * | |
| * \section sec_stream_disconnect Disconnect | |
| * | |
| * Use \ref pw_stream_disconnect() to disconnect a stream after use. | |
| * | |
| * \section sec_stream_configuration Configuration | |
| * | |
| * \subsection ssec_config_properties Stream Properties | |
| * | |
| * \subsection ssec_config_rules Stream Rules | |
| * | |
| * \section sec_stream_environment Environment Variables | |
| * | |
| * The environment variable PIPEWIRE_AUTOCONNECT can be used to override the | |
| * flag and force apps to autoconnect or not. | |
| * | |
| */ | |
| /** \defgroup pw_stream Stream | |
| * | |
| * \brief PipeWire stream objects | |
| * | |
| * The stream object provides a convenient way to send and | |
| * receive data streams from/to PipeWire. | |
| * | |
| * \see \ref page_streams, \ref api_pw_core | |
| */ | |
| /** | |
| * \addtogroup pw_stream | |
| * \{ | |
| */ | |
| struct pw_stream; | |
| #include <spa/buffer/buffer.h> | |
| #include <spa/param/param.h> | |
| #include <spa/pod/command.h> | |
| #include <spa/pod/event.h> | |
| /** \enum pw_stream_state The state of a stream */ | |
| enum pw_stream_state { | |
| PW_STREAM_STATE_ERROR = -1, /**< the stream is in error */ | |
| PW_STREAM_STATE_UNCONNECTED = 0, /**< unconnected */ | |
| PW_STREAM_STATE_CONNECTING = 1, /**< connection is in progress */ | |
| PW_STREAM_STATE_PAUSED = 2, /**< paused */ | |
| PW_STREAM_STATE_STREAMING = 3 /**< streaming */ | |
| }; | |
| /** a buffer structure obtained from pw_stream_dequeue_buffer(). The size of this | |
| * structure can grow as more fields are added in the future */ | |
| struct pw_buffer { | |
| struct spa_buffer *buffer; /**< the spa buffer */ | |
| void *user_data; /**< user data attached to the buffer. The user of | |
| * the stream can set custom data associated with the | |
| * buffer, typically in the add_buffer event. Any | |
| * cleanup should be performed in the remove_buffer | |
| * event. The user data is returned unmodified each | |
| * time a buffer is dequeued. */ | |
| uint64_t size; /**< This field is set by the user and the sum of | |
| * all queued buffers is returned in the time info. | |
| * For audio, it is advised to use the number of | |
| * frames in the buffer for this field. */ | |
| uint64_t requested; /**< For playback streams, this field contains the | |
| * suggested amount of data to provide. For audio | |
| * streams this will be the amount of frames | |
| * required by the resampler. This field is 0 | |
| * when no suggestion is provided. Since 0.3.49 */ | |
| uint64_t time; /**< For capture streams, this field contains the | |
| * cycle time in nanoseconds when this buffer was | |
| * queued in the stream. It can be compared against | |
| * the pw_time values or pw_stream_get_nsec() | |
| * Since 1.0.5 */ | |
| }; | |
| struct pw_stream_control { | |
| const char *name; /**< name of the control */ | |
| uint32_t flags; /**< extra flags (unused) */ | |
| float def; /**< default value */ | |
| float min; /**< min value */ | |
| float max; /**< max value */ | |
| float *values; /**< array of values */ | |
| uint32_t n_values; /**< number of values in array */ | |
| uint32_t max_values; /**< max values that can be set on this control */ | |
| }; | |
| /** A time structure. | |
| * | |
| * Use pw_stream_get_time_n() to get an updated time snapshot of the stream. | |
| * The time snapshot can give information about the time in the driver of the | |
| * graph, the delay to the edge of the graph and the internal queuing in the | |
| * stream. | |
| * | |
| * pw_time.ticks gives a monotonic increasing counter of the time in the graph | |
| * driver. I can be used to generate a timetime to schedule samples as well | |
| * as detect discontinuities in the timeline caused by xruns. | |
| * | |
| * pw_time.delay is expressed as pw_time.rate, the time domain of the graph. This | |
| * value, and pw_time.ticks, were captured at pw_time.now and can be extrapolated | |
| * to the current time like this: | |
| * | |
| *\code{.c} | |
| * uint64_t now = pw_stream_get_nsec(stream); | |
| * int64_t diff = now - pw_time.now; | |
| * int64_t elapsed = (pw_time.rate.denom * diff) / (pw_time.rate.num * SPA_NSEC_PER_SEC); | |
| *\endcode | |
| * | |
| * pw_time.delay contains the total delay that a signal will travel through the | |
| * graph. This includes the delay caused by filters in the graph as well as delays | |
| * caused by the hardware. The delay is usually quite stable and should only change when | |
| * the topology, quantum or samplerate of the graph changes. | |
| * | |
| * The delay requires the application to send the stream early relative to other synchronized | |
| * streams in order to arrive at the edge of the graph in time. This is usually done by | |
| * delaying the other streams with the given delay. | |
| * | |
| * Note that the delay can be negative. A negative delay means that this stream should be | |
| * delayed with the (positive) delay relative to other streams. | |
| * | |
| * pw_time.queued and pw_time.buffered is expressed in the time domain of the stream, | |
| * or the format that is used for the buffers of this stream. | |
| * | |
| * pw_time.queued is the sum of all the pw_buffer.size fields of the buffers that are | |
| * currently queued in the stream but not yet processed. The application can choose | |
| * the units of this value, for example, time, samples, frames or bytes (below | |
| * expressed as app.rate). | |
| * | |
| * pw_time.buffered is format dependent, for audio/raw it contains the number of frames | |
| * that are buffered inside the resampler/converter. | |
| * | |
| * The total delay of data in a stream is the sum of the queued and buffered data | |
| * (not yet processed data) and the delay to the edge of the graph, usually a | |
| * playback or capture device. | |
| * | |
| * For an audio playback stream, if you were to queue a buffer, the total delay | |
| * in milliseconds for the first sample in the newly queued buffer to be played | |
| * by the hardware can be calculated as: | |
| * | |
| *\code{.unparsed} | |
| * (pw_time.buffered * 1000 / stream.samplerate) + | |
| * (pw_time.queued * 1000 / app.rate) + | |
| * ((pw_time.delay - elapsed) * 1000 * pw_time.rate.num / pw_time.rate.denom) | |
| *\endcode | |
| * | |
| * The current extrapolated time (in ms) in the source or sink can be calculated as: | |
| * | |
| *\code{.unparsed} | |
| * (pw_time.ticks + elapsed) * 1000 * pw_time.rate.num / pw_time.rate.denom | |
| *\endcode | |
| * | |
| * Below is an overview of the different timing values: | |
| * | |
| *\code{.unparsed} | |
| * stream time domain graph time domain | |
| * /-----------------------\/-----------------------------\ | |
| * | |
| * queue +-+ +-+ +-----------+ +--------+ | |
| * ----> | | | |->| converter | -> graph -> | kernel | -> speaker | |
| * <---- +-+ +-+ +-----------+ +--------+ | |
| * dequeue buffers \-------------------/\--------/ | |
| * graph internal | |
| * latency latency | |
| * \--------/\-------------/\-----------------------------/ | |
| * queued buffered delay | |
| *\endcode | |
| */ | |
| struct pw_time { | |
| int64_t now; /**< the time in nanoseconds. This is the time when this | |
| * time report was updated. It is usually updated every | |
| * graph cycle. You can use pw_stream_get_nsec() to | |
| * calculate the elapsed time between this report and | |
| * the current time and calculate updated ticks and delay | |
| * values. */ | |
| struct spa_fraction rate; /**< the rate of \a ticks and delay. This is usually | |
| * expressed in 1/<samplerate>. */ | |
| uint64_t ticks; /**< the ticks at \a now. This is the current time that | |
| * the remote end is reading/writing. This is monotonicaly | |
| * increasing. */ | |
| int64_t delay; /**< delay to device. This is the time it will take for | |
| * the next output sample of the stream to be presented by | |
| * the playback device or the time a sample traveled | |
| * from the capture device. This delay includes the | |
| * delay introduced by all filters on the path between | |
| * the stream and the device. The delay is normally | |
| * constant in a graph and can change when the topology | |
| * of the graph or the quantum changes. This delay does | |
| * not include the delay caused by queued buffers. */ | |
| uint64_t queued; /**< data queued in the stream, this is the sum | |
| * of the size fields in the pw_buffer that are | |
| * currently queued */ | |
| uint64_t buffered; /**< for audio/raw streams, this contains the extra | |
| * number of frames buffered in the resampler. | |
| * Since 0.3.50. */ | |
| uint32_t queued_buffers; /**< the number of buffers that are queued. Since 0.3.50 */ | |
| uint32_t avail_buffers; /**< the number of buffers that can be dequeued. Since 0.3.50 */ | |
| uint64_t size; /**< for audio/raw playback streams, this contains the number of | |
| * samples requested by the resampler for the current | |
| * quantum. for audio/raw capture streams this will be the number | |
| * of samples available for the current quantum. Since 1.1.0 */ | |
| }; | |
| #include <pipewire/port.h> | |
| /** Events for a stream. These events are always called from the mainloop | |
| * unless explicitly documented otherwise. */ | |
| struct pw_stream_events { | |
| #define PW_VERSION_STREAM_EVENTS 2 | |
| uint32_t version; | |
| void (*destroy) (void *data); | |
| /** when the stream state changes */ | |
| void (*state_changed) (void *data, enum pw_stream_state old, | |
| enum pw_stream_state state, const char *error); | |
| /** Notify information about a control. */ | |
| void (*control_info) (void *data, uint32_t id, const struct pw_stream_control *control); | |
| /** when io changed on the stream. */ | |
| void (*io_changed) (void *data, uint32_t id, void *area, uint32_t size); | |
| /** when a parameter changed */ | |
| void (*param_changed) (void *data, uint32_t id, const struct spa_pod *param); | |
| /** when a new buffer was created for this stream */ | |
| void (*add_buffer) (void *data, struct pw_buffer *buffer); | |
| /** when a buffer was destroyed for this stream */ | |
| void (*remove_buffer) (void *data, struct pw_buffer *buffer); | |
| /** when a buffer can be queued (for playback streams) or | |
| * dequeued (for capture streams). This is normally called from the | |
| * mainloop but can also be called directly from the realtime data | |
| * thread if the user is prepared to deal with this. */ | |
| void (*process) (void *data); | |
| /** The stream is drained */ | |
| void (*drained) (void *data); | |
| /** A command notify, Since 0.3.39:1 */ | |
| void (*command) (void *data, const struct spa_command *command); | |
| /** a trigger_process completed. Since version 0.3.40:2. | |
| * This is normally called from the mainloop but since 1.1.0 it | |
| * can also be called directly from the realtime data | |
| * thread if the user is prepared to deal with this. */ | |
| void (*trigger_done) (void *data); | |
| }; | |
| /** Convert a stream state to a readable string */ | |
| const char * pw_stream_state_as_string(enum pw_stream_state state); | |
| /** \enum pw_stream_flags Extra flags that can be used in \ref pw_stream_connect() */ | |
| enum pw_stream_flags { | |
| PW_STREAM_FLAG_NONE = 0, /**< no flags */ | |
| PW_STREAM_FLAG_AUTOCONNECT = (1 << 0), /**< try to automatically connect | |
| * this stream */ | |
| PW_STREAM_FLAG_INACTIVE = (1 << 1), /**< start the stream inactive, | |
| * pw_stream_set_active() needs to be | |
| * called explicitly */ | |
| PW_STREAM_FLAG_MAP_BUFFERS = (1 << 2), /**< mmap the buffers except DmaBuf that is not | |
| * explicitly marked as mappable. */ | |
| PW_STREAM_FLAG_DRIVER = (1 << 3), /**< be a driver */ | |
| PW_STREAM_FLAG_RT_PROCESS = (1 << 4), /**< call process from the realtime | |
| * thread. You MUST use RT safe functions | |
| * in the process callback. */ | |
| PW_STREAM_FLAG_NO_CONVERT = (1 << 5), /**< don't convert format */ | |
| PW_STREAM_FLAG_EXCLUSIVE = (1 << 6), /**< require exclusive access to the | |
| * device */ | |
| PW_STREAM_FLAG_DONT_RECONNECT = (1 << 7), /**< don't try to reconnect this stream | |
| * when the sink/source is removed */ | |
| PW_STREAM_FLAG_ALLOC_BUFFERS = (1 << 8), /**< the application will allocate buffer | |
| * memory. In the add_buffer event, the | |
| * data of the buffer should be set */ | |
| PW_STREAM_FLAG_TRIGGER = (1 << 9), /**< the output stream will not be scheduled | |
| * automatically but _trigger_process() | |
| * needs to be called. This can be used | |
| * when the output of the stream depends | |
| * on input from other streams. */ | |
| PW_STREAM_FLAG_ASYNC = (1 << 10), /**< Buffers will not be dequeued/queued from | |
| * the realtime process() function. This is | |
| * assumed when RT_PROCESS is unset but can | |
| * also be the case when the process() function | |
| * does a trigger_process() that will then | |
| * dequeue/queue a buffer from another process() | |
| * function. since 0.3.73 */ | |
| PW_STREAM_FLAG_EARLY_PROCESS = (1 << 11), /**< Call process as soon as there is a buffer | |
| * to dequeue. This is only relevant for | |
| * playback and when not using RT_PROCESS. It | |
| * can be used to keep the maximum number of | |
| * buffers queued. Since 0.3.81 */ | |
| PW_STREAM_FLAG_RT_TRIGGER_DONE = (1 << 12), /**< Call trigger_done from the realtime | |
| * thread. You MUST use RT safe functions | |
| * in the trigger_done callback. Since 1.1.0 */ | |
| }; | |
| /** Create a new unconnected \ref pw_stream | |
| * \return a newly allocated \ref pw_stream */ | |
| struct pw_stream * | |
| pw_stream_new(struct pw_core *core, /**< a \ref pw_core */ | |
| const char *name, /**< a stream media name */ | |
| struct pw_properties *props /**< stream properties, ownership is taken */); | |
| struct pw_stream * | |
| pw_stream_new_simple(struct pw_loop *loop, /**< a \ref pw_loop to use as the main loop */ | |
| const char *name, /**< a stream media name */ | |
| struct pw_properties *props,/**< stream properties, ownership is taken */ | |
| const struct pw_stream_events *events, /**< stream events */ | |
| void *data /**< data passed to events */); | |
| /** Destroy a stream */ | |
| void pw_stream_destroy(struct pw_stream *stream); | |
| void pw_stream_add_listener(struct pw_stream *stream, | |
| struct spa_hook *listener, | |
| const struct pw_stream_events *events, | |
| void *data); | |
| enum pw_stream_state pw_stream_get_state(struct pw_stream *stream, const char **error); | |
| const char *pw_stream_get_name(struct pw_stream *stream); | |
| struct pw_core *pw_stream_get_core(struct pw_stream *stream); | |
| const struct pw_properties *pw_stream_get_properties(struct pw_stream *stream); | |
| int pw_stream_update_properties(struct pw_stream *stream, const struct spa_dict *dict); | |
| /** Connect a stream for input or output on \a port_path. | |
| * \return 0 on success < 0 on error. | |
| * | |
| * You should connect to the process event and use pw_stream_dequeue_buffer() | |
| * to get the latest metadata and data. */ | |
| int | |
| pw_stream_connect(struct pw_stream *stream, /**< a \ref pw_stream */ | |
| enum pw_direction direction, /**< the stream direction */ | |
| uint32_t target_id, /**< should have the value PW_ID_ANY. | |
| * To select a specific target | |
| * node, specify the | |
| * PW_KEY_OBJECT_SERIAL or the | |
| * PW_KEY_NODE_NAME value of the target | |
| * node in the PW_KEY_TARGET_OBJECT | |
| * property of the stream. | |
| * Specifying target nodes by | |
| * their id is deprecated. | |
| */ | |
| enum pw_stream_flags flags, /**< stream flags */ | |
| const struct spa_pod **params, /**< an array with params. The params | |
| * should ideally contain supported | |
| * formats. */ | |
| uint32_t n_params /**< number of items in \a params */); | |
| /** Get the node ID of the stream. | |
| * \return node ID. */ | |
| uint32_t | |
| pw_stream_get_node_id(struct pw_stream *stream); | |
| /** Disconnect \a stream */ | |
| int pw_stream_disconnect(struct pw_stream *stream); | |
| /** Set the stream in error state */ | |
| int pw_stream_set_error(struct pw_stream *stream, /**< a \ref pw_stream */ | |
| int res, /**< a result code */ | |
| const char *error, /**< an error message */ | |
| ...) SPA_PRINTF_FUNC(3, 4); | |
| /** Update the param exposed on the stream. */ | |
| int | |
| pw_stream_update_params(struct pw_stream *stream, /**< a \ref pw_stream */ | |
| const struct spa_pod **params, /**< an array of params. */ | |
| uint32_t n_params /**< number of elements in \a params */); | |
| /** | |
| * Set a parameter on the stream. This is like pw_stream_set_control() but with | |
| * a complete spa_pod param. It can also be called from the param_changed event handler | |
| * to intercept and modify the param for the adapter. Since 0.3.70 */ | |
| int pw_stream_set_param(struct pw_stream *stream, /**< a \ref pw_stream */ | |
| uint32_t id, /**< the id of the param */ | |
| const struct spa_pod *param /**< the params to set */); | |
| /** Get control values */ | |
| const struct pw_stream_control *pw_stream_get_control(struct pw_stream *stream, uint32_t id); | |
| /** Set control values */ | |
| int pw_stream_set_control(struct pw_stream *stream, uint32_t id, uint32_t n_values, float *values, ...); | |
| /** Query the time on the stream, RT safe */ | |
| int pw_stream_get_time_n(struct pw_stream *stream, struct pw_time *time, size_t size); | |
| /** Get the current time in nanoseconds. This value can be compared with | |
| * the \ref pw_time.now value. RT safe. Since 1.1.0 */ | |
| uint64_t pw_stream_get_nsec(struct pw_stream *stream); | |
| /** Get the data loop that is doing the processing of this stream. This loop | |
| * is assigned after pw_stream_connect(). * Since 1.1.0 */ | |
| struct pw_loop *pw_stream_get_data_loop(struct pw_stream *stream); | |
| /** Query the time on the stream, deprecated since 0.3.50, | |
| * use pw_stream_get_time_n() to get the fields added since 0.3.50. RT safe. */ | |
| SPA_DEPRECATED | |
| int pw_stream_get_time(struct pw_stream *stream, struct pw_time *time); | |
| /** Get a buffer that can be filled for playback streams or consumed | |
| * for capture streams. RT safe. */ | |
| struct pw_buffer *pw_stream_dequeue_buffer(struct pw_stream *stream); | |
| /** Submit a buffer for playback or recycle a buffer for capture. RT safe. */ | |
| int pw_stream_queue_buffer(struct pw_stream *stream, struct pw_buffer *buffer); | |
| /** Return a buffer to the queue without using it. This makes the buffer | |
| * immediately available to dequeue again. RT safe. */ | |
| int pw_stream_return_buffer(struct pw_stream *stream, struct pw_buffer *buffer); | |
| /** Activate or deactivate the stream */ | |
| int pw_stream_set_active(struct pw_stream *stream, bool active); | |
| /** Flush a stream. When \a drain is true, the drained callback will | |
| * be called when all data is played or recorded. The stream can be resumed | |
| * after the drain by setting it active again with | |
| * \ref pw_stream_set_active(). A flush without a drain is mostly useful afer | |
| * a state change to PAUSED, to flush any remaining data from the queues and | |
| * the converters. RT safe. */ | |
| int pw_stream_flush(struct pw_stream *stream, bool drain); | |
| /** Check if the stream is driving. The stream needs to have the | |
| * PW_STREAM_FLAG_DRIVER set. When the stream is driving, | |
| * pw_stream_trigger_process() needs to be called when data is | |
| * available (output) or needed (input). Since 0.3.34 */ | |
| bool pw_stream_is_driving(struct pw_stream *stream); | |
| /** Check if the graph is using lazy scheduling. If the stream is | |
| * driving according to \ref pw_stream_is_driving(), then it should | |
| * consider taking into account the RequestProcess commands when | |
| * driving the graph. | |
| * | |
| * If the stream is not driving, it should send out RequestProcess | |
| * events with \ref pw_stream_emit_event() or indirectly with | |
| * \ref pw_stream_trigger_process() to suggest a new graph cycle | |
| * to the driver. | |
| * | |
| * It is not a requirement that all RequestProcess events/commands | |
| * need to start a graph cycle. | |
| * Since 1.4.0 */ | |
| bool pw_stream_is_lazy(struct pw_stream *stream); | |
| /** Trigger a push/pull on the stream. One iteration of the graph will | |
| * be scheduled when the stream is driving according to | |
| * \ref pw_stream_is_driving(). If it successfully finishes, process() | |
| * will be called and the trigger_done event will be emitted. It is | |
| * possible for the graph iteration to not finish, so | |
| * pw_stream_trigger_process() needs to be called again even if process() | |
| * and trigger_done is not called. | |
| * | |
| * If there is a deadline after which the stream will have xrun, | |
| * pw_stream_trigger_process() should be called then, whether or not | |
| * process()/trigger_done has been called. Sound hardware will xrun if | |
| * there is any delay in audio processing, so the ALSA plugin triggers the | |
| * graph every quantum to ensure audio keeps flowing. Drivers that | |
| * do not have a deadline, such as the freewheel driver, should | |
| * use a timeout to ensure that forward progress keeps being made. | |
| * A reasonable choice of deadline is three times the quantum: if | |
| * the graph is taking 3x longer than normal, it is likely that it | |
| * is hung and should be retriggered. | |
| * | |
| * Streams that are not drivers according to \ref pw_stream_is_driving() | |
| * can also call this method. The result is that a RequestProcess event | |
| * is sent to the driver. If the graph is lazy scheduling according to | |
| * \ref pw_stream_is_lazy(), this might result in a graph cycle by the | |
| * driver. If the graph is not lazy scheduling and the stream is not a | |
| * driver, this method will have no effect. | |
| * | |
| * RT safe. | |
| * | |
| * Since 0.3.34 */ | |
| int pw_stream_trigger_process(struct pw_stream *stream); | |
| /** Emit an event from this stream. RT safe. | |
| * Since 1.2.6 */ | |
| int pw_stream_emit_event(struct pw_stream *stream, const struct spa_event *event); | |
| /** Adjust the rate of the stream. | |
| * When the stream is using an adaptive resampler, adjust the resampler rate. | |
| * When there is no resampler, -ENOTSUP is returned. Activating the adaptive | |
| * resampler will add a small amount of delay to the samples, you can deactivate | |
| * it again by setting a value <= 0.0. RT safe. | |
| * Since 1.4.0 */ | |
| int pw_stream_set_rate(struct pw_stream *stream, double rate); | |
| /** | |
| * \} | |
| */ | |
| #ifdef __cplusplus | |
| } | |
| #endif | |
| #endif /* PIPEWIRE_STREAM_H */ |