diff mbox series

[1/1] package/weston: add patch to support pipewire 0.3 API

Message ID 20200905171440.744310-1-james.hilliard1@gmail.com
State New
Headers show
Series [1/1] package/weston: add patch to support pipewire 0.3 API | expand

Commit Message

James Hilliard Sept. 5, 2020, 5:14 p.m. UTC
This is required when building weston against the latest pipewire
release.

Signed-off-by: James Hilliard <james.hilliard1@gmail.com>
---
 ...001-pipewire-add-support-for-0.3-API.patch | 391 ++++++++++++++++++
 1 file changed, 391 insertions(+)
 create mode 100644 package/weston/0001-pipewire-add-support-for-0.3-API.patch

Comments

Yann E. MORIN Sept. 5, 2020, 6:03 p.m. UTC | #1
James, All,

On 2020-09-05 11:14 -0600, James Hilliard spake thusly:
> This is required when building weston against the latest pipewire
> release.

But we only have pipewire 0.2.7 in Buildroot, so this patch is not
needed.

Ah but I see now that there is a patch pending to update pipewire. This
shouold have been mentioned as a post-commit note, so that would have
allowed me to spare a few minutes to understand why you would want to
fix that...

Besides, some questions were raised about your pipewire bump, and we are
waiting for your feedback...

Regards,
Yann E. MORIN.

> Signed-off-by: James Hilliard <james.hilliard1@gmail.com>
> ---
>  ...001-pipewire-add-support-for-0.3-API.patch | 391 ++++++++++++++++++
>  1 file changed, 391 insertions(+)
>  create mode 100644 package/weston/0001-pipewire-add-support-for-0.3-API.patch
> 
> diff --git a/package/weston/0001-pipewire-add-support-for-0.3-API.patch b/package/weston/0001-pipewire-add-support-for-0.3-API.patch
> new file mode 100644
> index 0000000000..b486b3de5c
> --- /dev/null
> +++ b/package/weston/0001-pipewire-add-support-for-0.3-API.patch
> @@ -0,0 +1,391 @@
> +From cc08737e3fd174ec3c4c208ea4f2a3a6a9e8af3e Mon Sep 17 00:00:00 2001
> +From: James Hilliard <james.hilliard1@gmail.com>
> +Date: Mon, 6 Jul 2020 00:58:02 -0600
> +Subject: [PATCH] pipewire: add support for 0.3 API
> +
> +Fixes: #369
> +
> +Signed-off-by: James Hilliard <james.hilliard1@gmail.com>
> +[james.hilliard1@gmail.com: backport from upstream commit
> +80b585f8d2a31e780b4de41fbd187a742bea7e1a]
> +---
> + .gitlab-ci.yml               |   2 +-
> + .gitlab-ci/debian-install.sh |  16 ++++-
> + pipewire/meson.build         |  28 ++++++---
> + pipewire/pipewire-plugin.c   | 118 ++++++++++++++++++++++++++++++++++-
> + 4 files changed, 151 insertions(+), 13 deletions(-)
> +
> +diff --git a/pipewire/meson.build b/pipewire/meson.build
> +index 3d3374b8..e30a0b62 100644
> +--- a/pipewire/meson.build
> ++++ b/pipewire/meson.build
> +@@ -5,17 +5,25 @@ if get_option('pipewire')
> + 		error('Attempting to build the pipewire plugin without the required DRM backend. ' + user_hint)
> + 	endif
> + 
> +-	depnames = [
> +-		'libpipewire-0.2', 'libspa-0.1'
> +-	]
> + 	deps_pipewire = [ dep_libweston_private ]
> +-	foreach depname : depnames
> +-		dep = dependency(depname, required: false)
> +-		if not dep.found()
> +-			error('Pipewire plugin requires @0@ which was not found. '.format(depname) + user_hint)
> +-		endif
> +-		deps_pipewire += dep
> +-	endforeach
> ++
> ++	dep_libpipewire = dependency('libpipewire-0.3', required: false)
> ++	if not dep_libpipewire.found()
> ++		dep_libpipewire = dependency('libpipewire-0.2', required: false)
> ++	endif
> ++	if not dep_libpipewire.found()
> ++		error('Pipewire plugin requires libpipewire which was not found. ' + user_hint)
> ++	endif
> ++	deps_pipewire += dep_libpipewire
> ++
> ++	dep_libspa = dependency('libspa-0.2', required: false)
> ++	if not dep_libspa.found()
> ++		dep_libspa = dependency('libspa-0.1', required: false)
> ++	endif
> ++	if not dep_libspa.found()
> ++		error('Pipewire plugin requires libspa which was not found. ' + user_hint)
> ++	endif
> ++	deps_pipewire += dep_libspa
> + 
> + 	plugin_pipewire = shared_library(
> + 		'pipewire-plugin',
> +diff --git a/pipewire/pipewire-plugin.c b/pipewire/pipewire-plugin.c
> +index 6f892574..ce70ea63 100644
> +--- a/pipewire/pipewire-plugin.c
> ++++ b/pipewire/pipewire-plugin.c
> +@@ -34,20 +34,27 @@
> + #include <errno.h>
> + #include <unistd.h>
> + 
> ++#include <pipewire/pipewire.h>
> ++
> + #include <spa/param/format-utils.h>
> + #include <spa/param/video/format-utils.h>
> + #include <spa/utils/defs.h>
> + 
> +-#include <pipewire/pipewire.h>
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++#include <spa/buffer/meta.h>
> ++#include <spa/utils/result.h>
> ++#endif
> + 
> + #define PROP_RANGE(min, max) 2, (min), (max)
> + 
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + struct type {
> + 	struct spa_type_media_type media_type;
> + 	struct spa_type_media_subtype media_subtype;
> + 	struct spa_type_format_video format_video;
> + 	struct spa_type_video_format video_format;
> + };
> ++#endif
> + 
> + struct weston_pipewire {
> + 	struct weston_compositor *compositor;
> +@@ -60,12 +67,19 @@ struct weston_pipewire {
> + 	struct pw_loop *loop;
> + 	struct wl_event_source *loop_source;
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	struct pw_context *context;
> ++#endif
> + 	struct pw_core *core;
> + 	struct pw_type *t;
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	struct spa_hook core_listener;
> ++#else
> + 	struct type type;
> + 
> + 	struct pw_remote *remote;
> + 	struct spa_hook remote_listener;
> ++#endif
> + };
> + 
> + struct pipewire_output {
> +@@ -100,6 +114,7 @@ struct pipewire_frame_data {
> + 	struct wl_event_source *fence_sync_event_source;
> + };
> + 
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + static inline void init_type(struct type *type, struct spa_type_map *map)
> + {
> + 	spa_type_media_type_map(map, &type->media_type);
> +@@ -107,6 +122,7 @@ static inline void init_type(struct type *type, struct spa_type_map *map)
> + 	spa_type_format_video_map(map, &type->format_video);
> + 	spa_type_video_format_map(map, &type->video_format);
> + }
> ++#endif
> + 
> + static void
> + pipewire_debug_impl(struct weston_pipewire *pipewire,
> +@@ -141,6 +157,7 @@ pipewire_debug_impl(struct weston_pipewire *pipewire,
> + 	free(logstr);
> + }
> + 
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + static void
> + pipewire_debug(struct weston_pipewire *pipewire, const char *fmt, ...)
> + {
> +@@ -150,6 +167,7 @@ pipewire_debug(struct weston_pipewire *pipewire, const char *fmt, ...)
> + 	pipewire_debug_impl(pipewire, NULL, fmt, ap);
> + 	va_end(ap);
> + }
> ++#endif
> + 
> + static void
> + pipewire_output_debug(struct pipewire_output *output, const char *fmt, ...)
> +@@ -185,7 +203,9 @@ pipewire_output_handle_frame(struct pipewire_output *output, int fd,
> + 	const struct weston_drm_virtual_output_api *api =
> + 		output->pipewire->virtual_output_api;
> + 	size_t size = output->output->height * stride;
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + 	struct pw_type *t = output->pipewire->t;
> ++#endif
> + 	struct pw_buffer *buffer;
> + 	struct spa_buffer *spa_buffer;
> + 	struct spa_meta_header *h;
> +@@ -203,7 +223,12 @@ pipewire_output_handle_frame(struct pipewire_output *output, int fd,
> + 
> + 	spa_buffer = buffer->buffer;
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	if ((h = spa_buffer_find_meta_data(spa_buffer, SPA_META_Header,
> ++				     sizeof(struct spa_meta_header)))) {
> ++#else
> + 	if ((h = spa_buffer_find_meta(spa_buffer, t->meta.Header))) {
> ++#endif
> + 		h->pts = -1;
> + 		h->flags = 0;
> + 		h->seq = output->seq++;
> +@@ -375,18 +400,40 @@ pipewire_set_dpms(struct weston_output *base_output, enum dpms_enum level)
> + static int
> + pipewire_output_connect(struct pipewire_output *output)
> + {
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + 	struct weston_pipewire *pipewire = output->pipewire;
> + 	struct type *type = &pipewire->type;
> ++#endif
> + 	uint8_t buffer[1024];
> + 	struct spa_pod_builder builder =
> + 		SPA_POD_BUILDER_INIT(buffer, sizeof(buffer));
> + 	const struct spa_pod *params[1];
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + 	struct pw_type *t = pipewire->t;
> ++#endif
> + 	int frame_rate = output->output->current_mode->refresh / 1000;
> + 	int width = output->output->width;
> + 	int height = output->output->height;
> + 	int ret;
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	params[0] = spa_pod_builder_add_object(&builder,
> ++		SPA_TYPE_OBJECT_Format, SPA_PARAM_EnumFormat,
> ++		SPA_FORMAT_mediaType, SPA_POD_Id(SPA_MEDIA_TYPE_video),
> ++		SPA_FORMAT_mediaSubtype, SPA_POD_Id(SPA_MEDIA_SUBTYPE_raw),
> ++		SPA_FORMAT_VIDEO_format, SPA_POD_Id(SPA_VIDEO_FORMAT_BGRx),
> ++		SPA_FORMAT_VIDEO_size, SPA_POD_Rectangle(&SPA_RECTANGLE(width, height)),
> ++		SPA_FORMAT_VIDEO_framerate, SPA_POD_Fraction(&SPA_FRACTION (0, 1)),
> ++		SPA_FORMAT_VIDEO_maxFramerate,
> ++		SPA_POD_CHOICE_RANGE_Fraction(&SPA_FRACTION(frame_rate, 1),
> ++			&SPA_FRACTION(1, 1),
> ++			&SPA_FRACTION(frame_rate, 1)));
> ++
> ++	ret = pw_stream_connect(output->stream, PW_DIRECTION_OUTPUT, SPA_ID_INVALID,
> ++				(PW_STREAM_FLAG_DRIVER |
> ++				 PW_STREAM_FLAG_MAP_BUFFERS),
> ++				params, 1);
> ++#else
> + 	params[0] = spa_pod_builder_object(&builder,
> + 		t->param.idEnumFormat, t->spa_format,
> + 		"I", type->media_type.video,
> +@@ -406,6 +453,7 @@ pipewire_output_connect(struct pipewire_output *output)
> + 				(PW_STREAM_FLAG_DRIVER |
> + 				 PW_STREAM_FLAG_MAP_BUFFERS),
> + 				params, 1);
> ++#endif
> + 	if (ret != 0) {
> + 		weston_log("Failed to connect pipewire stream: %s",
> + 			   spa_strerror(ret));
> +@@ -482,26 +530,42 @@ pipewire_output_stream_state_changed(void *data, enum pw_stream_state old,
> + }
> + 
> + static void
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++pipewire_output_stream_param_changed(void *data, uint32_t id, const struct spa_pod *format)
> ++#else
> + pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
> ++#endif
> + {
> + 	struct pipewire_output *output = data;
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + 	struct weston_pipewire *pipewire = output->pipewire;
> ++#endif
> + 	uint8_t buffer[1024];
> + 	struct spa_pod_builder builder =
> + 		SPA_POD_BUILDER_INIT(buffer, sizeof(buffer));
> + 	const struct spa_pod *params[2];
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + 	struct pw_type *t = pipewire->t;
> ++#endif
> + 	int32_t width, height, stride, size;
> + 	const int bpp = 4;
> + 
> + 	if (!format) {
> + 		pipewire_output_debug(output, "format = None");
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++		pw_stream_update_params(output->stream, NULL, 0);
> ++#else
> + 		pw_stream_finish_format(output->stream, 0, NULL, 0);
> ++#endif
> + 		return;
> + 	}
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	spa_format_video_raw_parse(format, &output->video_format);
> ++#else
> + 	spa_format_video_raw_parse(format, &output->video_format,
> + 				   &pipewire->type.format_video);
> ++#endif
> + 
> + 	width = output->video_format.size.width;
> + 	height = output->video_format.size.height;
> +@@ -510,6 +574,21 @@ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
> + 
> + 	pipewire_output_debug(output, "format = %dx%d", width, height);
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	params[0] = spa_pod_builder_add_object(&builder,
> ++		SPA_TYPE_OBJECT_ParamBuffers, SPA_PARAM_Buffers,
> ++		SPA_PARAM_BUFFERS_size, SPA_POD_Int(size),
> ++		SPA_PARAM_BUFFERS_stride, SPA_POD_Int(stride),
> ++		SPA_PARAM_BUFFERS_buffers, SPA_POD_CHOICE_RANGE_Int(4, 2, 8),
> ++		SPA_PARAM_BUFFERS_align, SPA_POD_Int(16));
> ++
> ++	params[1] = spa_pod_builder_add_object(&builder,
> ++		SPA_TYPE_OBJECT_ParamMeta, SPA_PARAM_Meta,
> ++		SPA_PARAM_META_type, SPA_POD_Id(SPA_META_Header),
> ++		SPA_PARAM_META_size, SPA_POD_Int(sizeof(struct spa_meta_header)));
> ++
> ++	pw_stream_update_params(output->stream, params, 2);
> ++#else
> + 	params[0] = spa_pod_builder_object(&builder,
> + 		t->param.idBuffers, t->param_buffers.Buffers,
> + 		":", t->param_buffers.size,
> +@@ -527,12 +606,17 @@ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
> + 		":", t->param_meta.size, "i", sizeof(struct spa_meta_header));
> + 
> + 	pw_stream_finish_format(output->stream, 0, params, 2);
> ++#endif
> + }
> + 
> + static const struct pw_stream_events stream_events = {
> + 	PW_VERSION_STREAM_EVENTS,
> + 	.state_changed = pipewire_output_stream_state_changed,
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	.param_changed = pipewire_output_stream_param_changed,
> ++#else
> + 	.format_changed = pipewire_output_stream_format_changed,
> ++#endif
> + };
> + 
> + static struct weston_output *
> +@@ -560,7 +644,11 @@ pipewire_output_create(struct weston_compositor *c, char *name)
> + 	if (!head)
> + 		goto err;
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	output->stream = pw_stream_new(pipewire->core, name, NULL);
> ++#else
> + 	output->stream = pw_stream_new(pipewire->remote, name, NULL);
> ++#endif
> + 	if (!output->stream) {
> + 		weston_log("Cannot initialize pipewire stream\n");
> + 		goto err;
> +@@ -704,6 +792,14 @@ weston_pipewire_loop_handler(int fd, uint32_t mask, void *data)
> + 	return 0;
> + }
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++static void
> ++weston_pipewire_error(void *data, uint32_t id, int seq, int res,
> ++			      const char *error)
> ++{
> ++	weston_log("pipewire remote error: %s\n", error);
> ++}
> ++#else
> + static void
> + weston_pipewire_state_changed(void *data, enum pw_remote_state old,
> + 			      enum pw_remote_state state, const char *error)
> +@@ -725,12 +821,20 @@ weston_pipewire_state_changed(void *data, enum pw_remote_state old,
> + 		break;
> + 	}
> + }
> ++#endif
> + 
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++static const struct pw_core_events core_events = {
> ++	PW_VERSION_CORE_EVENTS,
> ++	.error = weston_pipewire_error,
> ++};
> ++#else
> + static const struct pw_remote_events remote_events = {
> + 	PW_VERSION_REMOTE_EVENTS,
> + 	.state_changed = weston_pipewire_state_changed,
> + };
> ++#endif
> + 
> + static int
> + weston_pipewire_init(struct weston_pipewire *pipewire)
> +@@ -745,10 +849,19 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
> + 
> + 	pw_loop_enter(pipewire->loop);
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	pipewire->context = pw_context_new(pipewire->loop, NULL, 0);
> ++#else
> + 	pipewire->core = pw_core_new(pipewire->loop, NULL);
> + 	pipewire->t = pw_core_get_type(pipewire->core);
> + 	init_type(&pipewire->type, pipewire->t->map);
> ++#endif
> + 
> ++#if PW_CHECK_VERSION(0, 2, 90)
> ++	pw_core_add_listener(pipewire->core,
> ++			       &pipewire->core_listener,
> ++			       &core_events, pipewire);
> ++#else
> + 	pipewire->remote = pw_remote_new(pipewire->core, NULL, 0);
> + 	pw_remote_add_listener(pipewire->remote,
> + 			       &pipewire->remote_listener,
> +@@ -777,6 +890,7 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
> + 			goto err;
> + 		}
> + 	}
> ++#endif
> + 
> + 	loop = wl_display_get_event_loop(pipewire->compositor->wl_display);
> + 	pipewire->loop_source =
> +@@ -786,12 +900,14 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
> + 				     pipewire);
> + 
> + 	return 0;
> ++#if !PW_CHECK_VERSION(0, 2, 90)
> + err:
> + 	if (pipewire->remote)
> + 		pw_remote_destroy(pipewire->remote);
> + 	pw_loop_leave(pipewire->loop);
> + 	pw_loop_destroy(pipewire->loop);
> + 	return -1;
> ++#endif
> + }
> + 
> + static const struct weston_pipewire_api pipewire_api = {
> +-- 
> +2.25.1
> +
> -- 
> 2.25.1
>
James Hilliard Sept. 5, 2020, 6:13 p.m. UTC | #2
On Sat, Sep 5, 2020 at 12:03 PM Yann E. MORIN <yann.morin.1998@free.fr> wrote:
>
> James, All,
>
> On 2020-09-05 11:14 -0600, James Hilliard spake thusly:
> > This is required when building weston against the latest pipewire
> > release.
>
> But we only have pipewire 0.2.7 in Buildroot, so this patch is not
> needed.
>
> Ah but I see now that there is a patch pending to update pipewire. This
> shouold have been mentioned as a post-commit note, so that would have
> allowed me to spare a few minutes to understand why you would want to
> fix that...
>
> Besides, some questions were raised about your pipewire bump, and we are
> waiting for your feedback...
Yeah, still working on that.
>
> Regards,
> Yann E. MORIN.
>
> > Signed-off-by: James Hilliard <james.hilliard1@gmail.com>
> > ---
> >  ...001-pipewire-add-support-for-0.3-API.patch | 391 ++++++++++++++++++
> >  1 file changed, 391 insertions(+)
> >  create mode 100644 package/weston/0001-pipewire-add-support-for-0.3-API.patch
> >
> > diff --git a/package/weston/0001-pipewire-add-support-for-0.3-API.patch b/package/weston/0001-pipewire-add-support-for-0.3-API.patch
> > new file mode 100644
> > index 0000000000..b486b3de5c
> > --- /dev/null
> > +++ b/package/weston/0001-pipewire-add-support-for-0.3-API.patch
> > @@ -0,0 +1,391 @@
> > +From cc08737e3fd174ec3c4c208ea4f2a3a6a9e8af3e Mon Sep 17 00:00:00 2001
> > +From: James Hilliard <james.hilliard1@gmail.com>
> > +Date: Mon, 6 Jul 2020 00:58:02 -0600
> > +Subject: [PATCH] pipewire: add support for 0.3 API
> > +
> > +Fixes: #369
> > +
> > +Signed-off-by: James Hilliard <james.hilliard1@gmail.com>
> > +[james.hilliard1@gmail.com: backport from upstream commit
> > +80b585f8d2a31e780b4de41fbd187a742bea7e1a]
> > +---
> > + .gitlab-ci.yml               |   2 +-
> > + .gitlab-ci/debian-install.sh |  16 ++++-
> > + pipewire/meson.build         |  28 ++++++---
> > + pipewire/pipewire-plugin.c   | 118 ++++++++++++++++++++++++++++++++++-
> > + 4 files changed, 151 insertions(+), 13 deletions(-)
> > +
> > +diff --git a/pipewire/meson.build b/pipewire/meson.build
> > +index 3d3374b8..e30a0b62 100644
> > +--- a/pipewire/meson.build
> > ++++ b/pipewire/meson.build
> > +@@ -5,17 +5,25 @@ if get_option('pipewire')
> > +             error('Attempting to build the pipewire plugin without the required DRM backend. ' + user_hint)
> > +     endif
> > +
> > +-    depnames = [
> > +-            'libpipewire-0.2', 'libspa-0.1'
> > +-    ]
> > +     deps_pipewire = [ dep_libweston_private ]
> > +-    foreach depname : depnames
> > +-            dep = dependency(depname, required: false)
> > +-            if not dep.found()
> > +-                    error('Pipewire plugin requires @0@ which was not found. '.format(depname) + user_hint)
> > +-            endif
> > +-            deps_pipewire += dep
> > +-    endforeach
> > ++
> > ++    dep_libpipewire = dependency('libpipewire-0.3', required: false)
> > ++    if not dep_libpipewire.found()
> > ++            dep_libpipewire = dependency('libpipewire-0.2', required: false)
> > ++    endif
> > ++    if not dep_libpipewire.found()
> > ++            error('Pipewire plugin requires libpipewire which was not found. ' + user_hint)
> > ++    endif
> > ++    deps_pipewire += dep_libpipewire
> > ++
> > ++    dep_libspa = dependency('libspa-0.2', required: false)
> > ++    if not dep_libspa.found()
> > ++            dep_libspa = dependency('libspa-0.1', required: false)
> > ++    endif
> > ++    if not dep_libspa.found()
> > ++            error('Pipewire plugin requires libspa which was not found. ' + user_hint)
> > ++    endif
> > ++    deps_pipewire += dep_libspa
> > +
> > +     plugin_pipewire = shared_library(
> > +             'pipewire-plugin',
> > +diff --git a/pipewire/pipewire-plugin.c b/pipewire/pipewire-plugin.c
> > +index 6f892574..ce70ea63 100644
> > +--- a/pipewire/pipewire-plugin.c
> > ++++ b/pipewire/pipewire-plugin.c
> > +@@ -34,20 +34,27 @@
> > + #include <errno.h>
> > + #include <unistd.h>
> > +
> > ++#include <pipewire/pipewire.h>
> > ++
> > + #include <spa/param/format-utils.h>
> > + #include <spa/param/video/format-utils.h>
> > + #include <spa/utils/defs.h>
> > +
> > +-#include <pipewire/pipewire.h>
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++#include <spa/buffer/meta.h>
> > ++#include <spa/utils/result.h>
> > ++#endif
> > +
> > + #define PROP_RANGE(min, max) 2, (min), (max)
> > +
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > + struct type {
> > +     struct spa_type_media_type media_type;
> > +     struct spa_type_media_subtype media_subtype;
> > +     struct spa_type_format_video format_video;
> > +     struct spa_type_video_format video_format;
> > + };
> > ++#endif
> > +
> > + struct weston_pipewire {
> > +     struct weston_compositor *compositor;
> > +@@ -60,12 +67,19 @@ struct weston_pipewire {
> > +     struct pw_loop *loop;
> > +     struct wl_event_source *loop_source;
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    struct pw_context *context;
> > ++#endif
> > +     struct pw_core *core;
> > +     struct pw_type *t;
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    struct spa_hook core_listener;
> > ++#else
> > +     struct type type;
> > +
> > +     struct pw_remote *remote;
> > +     struct spa_hook remote_listener;
> > ++#endif
> > + };
> > +
> > + struct pipewire_output {
> > +@@ -100,6 +114,7 @@ struct pipewire_frame_data {
> > +     struct wl_event_source *fence_sync_event_source;
> > + };
> > +
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > + static inline void init_type(struct type *type, struct spa_type_map *map)
> > + {
> > +     spa_type_media_type_map(map, &type->media_type);
> > +@@ -107,6 +122,7 @@ static inline void init_type(struct type *type, struct spa_type_map *map)
> > +     spa_type_format_video_map(map, &type->format_video);
> > +     spa_type_video_format_map(map, &type->video_format);
> > + }
> > ++#endif
> > +
> > + static void
> > + pipewire_debug_impl(struct weston_pipewire *pipewire,
> > +@@ -141,6 +157,7 @@ pipewire_debug_impl(struct weston_pipewire *pipewire,
> > +     free(logstr);
> > + }
> > +
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > + static void
> > + pipewire_debug(struct weston_pipewire *pipewire, const char *fmt, ...)
> > + {
> > +@@ -150,6 +167,7 @@ pipewire_debug(struct weston_pipewire *pipewire, const char *fmt, ...)
> > +     pipewire_debug_impl(pipewire, NULL, fmt, ap);
> > +     va_end(ap);
> > + }
> > ++#endif
> > +
> > + static void
> > + pipewire_output_debug(struct pipewire_output *output, const char *fmt, ...)
> > +@@ -185,7 +203,9 @@ pipewire_output_handle_frame(struct pipewire_output *output, int fd,
> > +     const struct weston_drm_virtual_output_api *api =
> > +             output->pipewire->virtual_output_api;
> > +     size_t size = output->output->height * stride;
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > +     struct pw_type *t = output->pipewire->t;
> > ++#endif
> > +     struct pw_buffer *buffer;
> > +     struct spa_buffer *spa_buffer;
> > +     struct spa_meta_header *h;
> > +@@ -203,7 +223,12 @@ pipewire_output_handle_frame(struct pipewire_output *output, int fd,
> > +
> > +     spa_buffer = buffer->buffer;
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    if ((h = spa_buffer_find_meta_data(spa_buffer, SPA_META_Header,
> > ++                                 sizeof(struct spa_meta_header)))) {
> > ++#else
> > +     if ((h = spa_buffer_find_meta(spa_buffer, t->meta.Header))) {
> > ++#endif
> > +             h->pts = -1;
> > +             h->flags = 0;
> > +             h->seq = output->seq++;
> > +@@ -375,18 +400,40 @@ pipewire_set_dpms(struct weston_output *base_output, enum dpms_enum level)
> > + static int
> > + pipewire_output_connect(struct pipewire_output *output)
> > + {
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > +     struct weston_pipewire *pipewire = output->pipewire;
> > +     struct type *type = &pipewire->type;
> > ++#endif
> > +     uint8_t buffer[1024];
> > +     struct spa_pod_builder builder =
> > +             SPA_POD_BUILDER_INIT(buffer, sizeof(buffer));
> > +     const struct spa_pod *params[1];
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > +     struct pw_type *t = pipewire->t;
> > ++#endif
> > +     int frame_rate = output->output->current_mode->refresh / 1000;
> > +     int width = output->output->width;
> > +     int height = output->output->height;
> > +     int ret;
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    params[0] = spa_pod_builder_add_object(&builder,
> > ++            SPA_TYPE_OBJECT_Format, SPA_PARAM_EnumFormat,
> > ++            SPA_FORMAT_mediaType, SPA_POD_Id(SPA_MEDIA_TYPE_video),
> > ++            SPA_FORMAT_mediaSubtype, SPA_POD_Id(SPA_MEDIA_SUBTYPE_raw),
> > ++            SPA_FORMAT_VIDEO_format, SPA_POD_Id(SPA_VIDEO_FORMAT_BGRx),
> > ++            SPA_FORMAT_VIDEO_size, SPA_POD_Rectangle(&SPA_RECTANGLE(width, height)),
> > ++            SPA_FORMAT_VIDEO_framerate, SPA_POD_Fraction(&SPA_FRACTION (0, 1)),
> > ++            SPA_FORMAT_VIDEO_maxFramerate,
> > ++            SPA_POD_CHOICE_RANGE_Fraction(&SPA_FRACTION(frame_rate, 1),
> > ++                    &SPA_FRACTION(1, 1),
> > ++                    &SPA_FRACTION(frame_rate, 1)));
> > ++
> > ++    ret = pw_stream_connect(output->stream, PW_DIRECTION_OUTPUT, SPA_ID_INVALID,
> > ++                            (PW_STREAM_FLAG_DRIVER |
> > ++                             PW_STREAM_FLAG_MAP_BUFFERS),
> > ++                            params, 1);
> > ++#else
> > +     params[0] = spa_pod_builder_object(&builder,
> > +             t->param.idEnumFormat, t->spa_format,
> > +             "I", type->media_type.video,
> > +@@ -406,6 +453,7 @@ pipewire_output_connect(struct pipewire_output *output)
> > +                             (PW_STREAM_FLAG_DRIVER |
> > +                              PW_STREAM_FLAG_MAP_BUFFERS),
> > +                             params, 1);
> > ++#endif
> > +     if (ret != 0) {
> > +             weston_log("Failed to connect pipewire stream: %s",
> > +                        spa_strerror(ret));
> > +@@ -482,26 +530,42 @@ pipewire_output_stream_state_changed(void *data, enum pw_stream_state old,
> > + }
> > +
> > + static void
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++pipewire_output_stream_param_changed(void *data, uint32_t id, const struct spa_pod *format)
> > ++#else
> > + pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
> > ++#endif
> > + {
> > +     struct pipewire_output *output = data;
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > +     struct weston_pipewire *pipewire = output->pipewire;
> > ++#endif
> > +     uint8_t buffer[1024];
> > +     struct spa_pod_builder builder =
> > +             SPA_POD_BUILDER_INIT(buffer, sizeof(buffer));
> > +     const struct spa_pod *params[2];
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > +     struct pw_type *t = pipewire->t;
> > ++#endif
> > +     int32_t width, height, stride, size;
> > +     const int bpp = 4;
> > +
> > +     if (!format) {
> > +             pipewire_output_debug(output, "format = None");
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++            pw_stream_update_params(output->stream, NULL, 0);
> > ++#else
> > +             pw_stream_finish_format(output->stream, 0, NULL, 0);
> > ++#endif
> > +             return;
> > +     }
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    spa_format_video_raw_parse(format, &output->video_format);
> > ++#else
> > +     spa_format_video_raw_parse(format, &output->video_format,
> > +                                &pipewire->type.format_video);
> > ++#endif
> > +
> > +     width = output->video_format.size.width;
> > +     height = output->video_format.size.height;
> > +@@ -510,6 +574,21 @@ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
> > +
> > +     pipewire_output_debug(output, "format = %dx%d", width, height);
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    params[0] = spa_pod_builder_add_object(&builder,
> > ++            SPA_TYPE_OBJECT_ParamBuffers, SPA_PARAM_Buffers,
> > ++            SPA_PARAM_BUFFERS_size, SPA_POD_Int(size),
> > ++            SPA_PARAM_BUFFERS_stride, SPA_POD_Int(stride),
> > ++            SPA_PARAM_BUFFERS_buffers, SPA_POD_CHOICE_RANGE_Int(4, 2, 8),
> > ++            SPA_PARAM_BUFFERS_align, SPA_POD_Int(16));
> > ++
> > ++    params[1] = spa_pod_builder_add_object(&builder,
> > ++            SPA_TYPE_OBJECT_ParamMeta, SPA_PARAM_Meta,
> > ++            SPA_PARAM_META_type, SPA_POD_Id(SPA_META_Header),
> > ++            SPA_PARAM_META_size, SPA_POD_Int(sizeof(struct spa_meta_header)));
> > ++
> > ++    pw_stream_update_params(output->stream, params, 2);
> > ++#else
> > +     params[0] = spa_pod_builder_object(&builder,
> > +             t->param.idBuffers, t->param_buffers.Buffers,
> > +             ":", t->param_buffers.size,
> > +@@ -527,12 +606,17 @@ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
> > +             ":", t->param_meta.size, "i", sizeof(struct spa_meta_header));
> > +
> > +     pw_stream_finish_format(output->stream, 0, params, 2);
> > ++#endif
> > + }
> > +
> > + static const struct pw_stream_events stream_events = {
> > +     PW_VERSION_STREAM_EVENTS,
> > +     .state_changed = pipewire_output_stream_state_changed,
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    .param_changed = pipewire_output_stream_param_changed,
> > ++#else
> > +     .format_changed = pipewire_output_stream_format_changed,
> > ++#endif
> > + };
> > +
> > + static struct weston_output *
> > +@@ -560,7 +644,11 @@ pipewire_output_create(struct weston_compositor *c, char *name)
> > +     if (!head)
> > +             goto err;
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    output->stream = pw_stream_new(pipewire->core, name, NULL);
> > ++#else
> > +     output->stream = pw_stream_new(pipewire->remote, name, NULL);
> > ++#endif
> > +     if (!output->stream) {
> > +             weston_log("Cannot initialize pipewire stream\n");
> > +             goto err;
> > +@@ -704,6 +792,14 @@ weston_pipewire_loop_handler(int fd, uint32_t mask, void *data)
> > +     return 0;
> > + }
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++static void
> > ++weston_pipewire_error(void *data, uint32_t id, int seq, int res,
> > ++                          const char *error)
> > ++{
> > ++    weston_log("pipewire remote error: %s\n", error);
> > ++}
> > ++#else
> > + static void
> > + weston_pipewire_state_changed(void *data, enum pw_remote_state old,
> > +                           enum pw_remote_state state, const char *error)
> > +@@ -725,12 +821,20 @@ weston_pipewire_state_changed(void *data, enum pw_remote_state old,
> > +             break;
> > +     }
> > + }
> > ++#endif
> > +
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++static const struct pw_core_events core_events = {
> > ++    PW_VERSION_CORE_EVENTS,
> > ++    .error = weston_pipewire_error,
> > ++};
> > ++#else
> > + static const struct pw_remote_events remote_events = {
> > +     PW_VERSION_REMOTE_EVENTS,
> > +     .state_changed = weston_pipewire_state_changed,
> > + };
> > ++#endif
> > +
> > + static int
> > + weston_pipewire_init(struct weston_pipewire *pipewire)
> > +@@ -745,10 +849,19 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
> > +
> > +     pw_loop_enter(pipewire->loop);
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    pipewire->context = pw_context_new(pipewire->loop, NULL, 0);
> > ++#else
> > +     pipewire->core = pw_core_new(pipewire->loop, NULL);
> > +     pipewire->t = pw_core_get_type(pipewire->core);
> > +     init_type(&pipewire->type, pipewire->t->map);
> > ++#endif
> > +
> > ++#if PW_CHECK_VERSION(0, 2, 90)
> > ++    pw_core_add_listener(pipewire->core,
> > ++                           &pipewire->core_listener,
> > ++                           &core_events, pipewire);
> > ++#else
> > +     pipewire->remote = pw_remote_new(pipewire->core, NULL, 0);
> > +     pw_remote_add_listener(pipewire->remote,
> > +                            &pipewire->remote_listener,
> > +@@ -777,6 +890,7 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
> > +                     goto err;
> > +             }
> > +     }
> > ++#endif
> > +
> > +     loop = wl_display_get_event_loop(pipewire->compositor->wl_display);
> > +     pipewire->loop_source =
> > +@@ -786,12 +900,14 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
> > +                                  pipewire);
> > +
> > +     return 0;
> > ++#if !PW_CHECK_VERSION(0, 2, 90)
> > + err:
> > +     if (pipewire->remote)
> > +             pw_remote_destroy(pipewire->remote);
> > +     pw_loop_leave(pipewire->loop);
> > +     pw_loop_destroy(pipewire->loop);
> > +     return -1;
> > ++#endif
> > + }
> > +
> > + static const struct weston_pipewire_api pipewire_api = {
> > +--
> > +2.25.1
> > +
> > --
> > 2.25.1
> >
>
> --
> .-----------------.--------------------.------------------.--------------------.
> |  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
> | +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
> | +33 561 099 427 `------------.-------:  X  AGAINST      |  \e/  There is no  |
> | http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
> '------------------------------^-------^------------------^--------------------'
diff mbox series

Patch

diff --git a/package/weston/0001-pipewire-add-support-for-0.3-API.patch b/package/weston/0001-pipewire-add-support-for-0.3-API.patch
new file mode 100644
index 0000000000..b486b3de5c
--- /dev/null
+++ b/package/weston/0001-pipewire-add-support-for-0.3-API.patch
@@ -0,0 +1,391 @@ 
+From cc08737e3fd174ec3c4c208ea4f2a3a6a9e8af3e Mon Sep 17 00:00:00 2001
+From: James Hilliard <james.hilliard1@gmail.com>
+Date: Mon, 6 Jul 2020 00:58:02 -0600
+Subject: [PATCH] pipewire: add support for 0.3 API
+
+Fixes: #369
+
+Signed-off-by: James Hilliard <james.hilliard1@gmail.com>
+[james.hilliard1@gmail.com: backport from upstream commit
+80b585f8d2a31e780b4de41fbd187a742bea7e1a]
+---
+ .gitlab-ci.yml               |   2 +-
+ .gitlab-ci/debian-install.sh |  16 ++++-
+ pipewire/meson.build         |  28 ++++++---
+ pipewire/pipewire-plugin.c   | 118 ++++++++++++++++++++++++++++++++++-
+ 4 files changed, 151 insertions(+), 13 deletions(-)
+
+diff --git a/pipewire/meson.build b/pipewire/meson.build
+index 3d3374b8..e30a0b62 100644
+--- a/pipewire/meson.build
++++ b/pipewire/meson.build
+@@ -5,17 +5,25 @@ if get_option('pipewire')
+ 		error('Attempting to build the pipewire plugin without the required DRM backend. ' + user_hint)
+ 	endif
+ 
+-	depnames = [
+-		'libpipewire-0.2', 'libspa-0.1'
+-	]
+ 	deps_pipewire = [ dep_libweston_private ]
+-	foreach depname : depnames
+-		dep = dependency(depname, required: false)
+-		if not dep.found()
+-			error('Pipewire plugin requires @0@ which was not found. '.format(depname) + user_hint)
+-		endif
+-		deps_pipewire += dep
+-	endforeach
++
++	dep_libpipewire = dependency('libpipewire-0.3', required: false)
++	if not dep_libpipewire.found()
++		dep_libpipewire = dependency('libpipewire-0.2', required: false)
++	endif
++	if not dep_libpipewire.found()
++		error('Pipewire plugin requires libpipewire which was not found. ' + user_hint)
++	endif
++	deps_pipewire += dep_libpipewire
++
++	dep_libspa = dependency('libspa-0.2', required: false)
++	if not dep_libspa.found()
++		dep_libspa = dependency('libspa-0.1', required: false)
++	endif
++	if not dep_libspa.found()
++		error('Pipewire plugin requires libspa which was not found. ' + user_hint)
++	endif
++	deps_pipewire += dep_libspa
+ 
+ 	plugin_pipewire = shared_library(
+ 		'pipewire-plugin',
+diff --git a/pipewire/pipewire-plugin.c b/pipewire/pipewire-plugin.c
+index 6f892574..ce70ea63 100644
+--- a/pipewire/pipewire-plugin.c
++++ b/pipewire/pipewire-plugin.c
+@@ -34,20 +34,27 @@
+ #include <errno.h>
+ #include <unistd.h>
+ 
++#include <pipewire/pipewire.h>
++
+ #include <spa/param/format-utils.h>
+ #include <spa/param/video/format-utils.h>
+ #include <spa/utils/defs.h>
+ 
+-#include <pipewire/pipewire.h>
++#if PW_CHECK_VERSION(0, 2, 90)
++#include <spa/buffer/meta.h>
++#include <spa/utils/result.h>
++#endif
+ 
+ #define PROP_RANGE(min, max) 2, (min), (max)
+ 
++#if !PW_CHECK_VERSION(0, 2, 90)
+ struct type {
+ 	struct spa_type_media_type media_type;
+ 	struct spa_type_media_subtype media_subtype;
+ 	struct spa_type_format_video format_video;
+ 	struct spa_type_video_format video_format;
+ };
++#endif
+ 
+ struct weston_pipewire {
+ 	struct weston_compositor *compositor;
+@@ -60,12 +67,19 @@ struct weston_pipewire {
+ 	struct pw_loop *loop;
+ 	struct wl_event_source *loop_source;
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	struct pw_context *context;
++#endif
+ 	struct pw_core *core;
+ 	struct pw_type *t;
++#if PW_CHECK_VERSION(0, 2, 90)
++	struct spa_hook core_listener;
++#else
+ 	struct type type;
+ 
+ 	struct pw_remote *remote;
+ 	struct spa_hook remote_listener;
++#endif
+ };
+ 
+ struct pipewire_output {
+@@ -100,6 +114,7 @@ struct pipewire_frame_data {
+ 	struct wl_event_source *fence_sync_event_source;
+ };
+ 
++#if !PW_CHECK_VERSION(0, 2, 90)
+ static inline void init_type(struct type *type, struct spa_type_map *map)
+ {
+ 	spa_type_media_type_map(map, &type->media_type);
+@@ -107,6 +122,7 @@ static inline void init_type(struct type *type, struct spa_type_map *map)
+ 	spa_type_format_video_map(map, &type->format_video);
+ 	spa_type_video_format_map(map, &type->video_format);
+ }
++#endif
+ 
+ static void
+ pipewire_debug_impl(struct weston_pipewire *pipewire,
+@@ -141,6 +157,7 @@ pipewire_debug_impl(struct weston_pipewire *pipewire,
+ 	free(logstr);
+ }
+ 
++#if !PW_CHECK_VERSION(0, 2, 90)
+ static void
+ pipewire_debug(struct weston_pipewire *pipewire, const char *fmt, ...)
+ {
+@@ -150,6 +167,7 @@ pipewire_debug(struct weston_pipewire *pipewire, const char *fmt, ...)
+ 	pipewire_debug_impl(pipewire, NULL, fmt, ap);
+ 	va_end(ap);
+ }
++#endif
+ 
+ static void
+ pipewire_output_debug(struct pipewire_output *output, const char *fmt, ...)
+@@ -185,7 +203,9 @@ pipewire_output_handle_frame(struct pipewire_output *output, int fd,
+ 	const struct weston_drm_virtual_output_api *api =
+ 		output->pipewire->virtual_output_api;
+ 	size_t size = output->output->height * stride;
++#if !PW_CHECK_VERSION(0, 2, 90)
+ 	struct pw_type *t = output->pipewire->t;
++#endif
+ 	struct pw_buffer *buffer;
+ 	struct spa_buffer *spa_buffer;
+ 	struct spa_meta_header *h;
+@@ -203,7 +223,12 @@ pipewire_output_handle_frame(struct pipewire_output *output, int fd,
+ 
+ 	spa_buffer = buffer->buffer;
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	if ((h = spa_buffer_find_meta_data(spa_buffer, SPA_META_Header,
++				     sizeof(struct spa_meta_header)))) {
++#else
+ 	if ((h = spa_buffer_find_meta(spa_buffer, t->meta.Header))) {
++#endif
+ 		h->pts = -1;
+ 		h->flags = 0;
+ 		h->seq = output->seq++;
+@@ -375,18 +400,40 @@ pipewire_set_dpms(struct weston_output *base_output, enum dpms_enum level)
+ static int
+ pipewire_output_connect(struct pipewire_output *output)
+ {
++#if !PW_CHECK_VERSION(0, 2, 90)
+ 	struct weston_pipewire *pipewire = output->pipewire;
+ 	struct type *type = &pipewire->type;
++#endif
+ 	uint8_t buffer[1024];
+ 	struct spa_pod_builder builder =
+ 		SPA_POD_BUILDER_INIT(buffer, sizeof(buffer));
+ 	const struct spa_pod *params[1];
++#if !PW_CHECK_VERSION(0, 2, 90)
+ 	struct pw_type *t = pipewire->t;
++#endif
+ 	int frame_rate = output->output->current_mode->refresh / 1000;
+ 	int width = output->output->width;
+ 	int height = output->output->height;
+ 	int ret;
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	params[0] = spa_pod_builder_add_object(&builder,
++		SPA_TYPE_OBJECT_Format, SPA_PARAM_EnumFormat,
++		SPA_FORMAT_mediaType, SPA_POD_Id(SPA_MEDIA_TYPE_video),
++		SPA_FORMAT_mediaSubtype, SPA_POD_Id(SPA_MEDIA_SUBTYPE_raw),
++		SPA_FORMAT_VIDEO_format, SPA_POD_Id(SPA_VIDEO_FORMAT_BGRx),
++		SPA_FORMAT_VIDEO_size, SPA_POD_Rectangle(&SPA_RECTANGLE(width, height)),
++		SPA_FORMAT_VIDEO_framerate, SPA_POD_Fraction(&SPA_FRACTION (0, 1)),
++		SPA_FORMAT_VIDEO_maxFramerate,
++		SPA_POD_CHOICE_RANGE_Fraction(&SPA_FRACTION(frame_rate, 1),
++			&SPA_FRACTION(1, 1),
++			&SPA_FRACTION(frame_rate, 1)));
++
++	ret = pw_stream_connect(output->stream, PW_DIRECTION_OUTPUT, SPA_ID_INVALID,
++				(PW_STREAM_FLAG_DRIVER |
++				 PW_STREAM_FLAG_MAP_BUFFERS),
++				params, 1);
++#else
+ 	params[0] = spa_pod_builder_object(&builder,
+ 		t->param.idEnumFormat, t->spa_format,
+ 		"I", type->media_type.video,
+@@ -406,6 +453,7 @@ pipewire_output_connect(struct pipewire_output *output)
+ 				(PW_STREAM_FLAG_DRIVER |
+ 				 PW_STREAM_FLAG_MAP_BUFFERS),
+ 				params, 1);
++#endif
+ 	if (ret != 0) {
+ 		weston_log("Failed to connect pipewire stream: %s",
+ 			   spa_strerror(ret));
+@@ -482,26 +530,42 @@ pipewire_output_stream_state_changed(void *data, enum pw_stream_state old,
+ }
+ 
+ static void
++#if PW_CHECK_VERSION(0, 2, 90)
++pipewire_output_stream_param_changed(void *data, uint32_t id, const struct spa_pod *format)
++#else
+ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
++#endif
+ {
+ 	struct pipewire_output *output = data;
++#if !PW_CHECK_VERSION(0, 2, 90)
+ 	struct weston_pipewire *pipewire = output->pipewire;
++#endif
+ 	uint8_t buffer[1024];
+ 	struct spa_pod_builder builder =
+ 		SPA_POD_BUILDER_INIT(buffer, sizeof(buffer));
+ 	const struct spa_pod *params[2];
++#if !PW_CHECK_VERSION(0, 2, 90)
+ 	struct pw_type *t = pipewire->t;
++#endif
+ 	int32_t width, height, stride, size;
+ 	const int bpp = 4;
+ 
+ 	if (!format) {
+ 		pipewire_output_debug(output, "format = None");
++#if PW_CHECK_VERSION(0, 2, 90)
++		pw_stream_update_params(output->stream, NULL, 0);
++#else
+ 		pw_stream_finish_format(output->stream, 0, NULL, 0);
++#endif
+ 		return;
+ 	}
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	spa_format_video_raw_parse(format, &output->video_format);
++#else
+ 	spa_format_video_raw_parse(format, &output->video_format,
+ 				   &pipewire->type.format_video);
++#endif
+ 
+ 	width = output->video_format.size.width;
+ 	height = output->video_format.size.height;
+@@ -510,6 +574,21 @@ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
+ 
+ 	pipewire_output_debug(output, "format = %dx%d", width, height);
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	params[0] = spa_pod_builder_add_object(&builder,
++		SPA_TYPE_OBJECT_ParamBuffers, SPA_PARAM_Buffers,
++		SPA_PARAM_BUFFERS_size, SPA_POD_Int(size),
++		SPA_PARAM_BUFFERS_stride, SPA_POD_Int(stride),
++		SPA_PARAM_BUFFERS_buffers, SPA_POD_CHOICE_RANGE_Int(4, 2, 8),
++		SPA_PARAM_BUFFERS_align, SPA_POD_Int(16));
++
++	params[1] = spa_pod_builder_add_object(&builder,
++		SPA_TYPE_OBJECT_ParamMeta, SPA_PARAM_Meta,
++		SPA_PARAM_META_type, SPA_POD_Id(SPA_META_Header),
++		SPA_PARAM_META_size, SPA_POD_Int(sizeof(struct spa_meta_header)));
++
++	pw_stream_update_params(output->stream, params, 2);
++#else
+ 	params[0] = spa_pod_builder_object(&builder,
+ 		t->param.idBuffers, t->param_buffers.Buffers,
+ 		":", t->param_buffers.size,
+@@ -527,12 +606,17 @@ pipewire_output_stream_format_changed(void *data, const struct spa_pod *format)
+ 		":", t->param_meta.size, "i", sizeof(struct spa_meta_header));
+ 
+ 	pw_stream_finish_format(output->stream, 0, params, 2);
++#endif
+ }
+ 
+ static const struct pw_stream_events stream_events = {
+ 	PW_VERSION_STREAM_EVENTS,
+ 	.state_changed = pipewire_output_stream_state_changed,
++#if PW_CHECK_VERSION(0, 2, 90)
++	.param_changed = pipewire_output_stream_param_changed,
++#else
+ 	.format_changed = pipewire_output_stream_format_changed,
++#endif
+ };
+ 
+ static struct weston_output *
+@@ -560,7 +644,11 @@ pipewire_output_create(struct weston_compositor *c, char *name)
+ 	if (!head)
+ 		goto err;
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	output->stream = pw_stream_new(pipewire->core, name, NULL);
++#else
+ 	output->stream = pw_stream_new(pipewire->remote, name, NULL);
++#endif
+ 	if (!output->stream) {
+ 		weston_log("Cannot initialize pipewire stream\n");
+ 		goto err;
+@@ -704,6 +792,14 @@ weston_pipewire_loop_handler(int fd, uint32_t mask, void *data)
+ 	return 0;
+ }
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++static void
++weston_pipewire_error(void *data, uint32_t id, int seq, int res,
++			      const char *error)
++{
++	weston_log("pipewire remote error: %s\n", error);
++}
++#else
+ static void
+ weston_pipewire_state_changed(void *data, enum pw_remote_state old,
+ 			      enum pw_remote_state state, const char *error)
+@@ -725,12 +821,20 @@ weston_pipewire_state_changed(void *data, enum pw_remote_state old,
+ 		break;
+ 	}
+ }
++#endif
+ 
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++static const struct pw_core_events core_events = {
++	PW_VERSION_CORE_EVENTS,
++	.error = weston_pipewire_error,
++};
++#else
+ static const struct pw_remote_events remote_events = {
+ 	PW_VERSION_REMOTE_EVENTS,
+ 	.state_changed = weston_pipewire_state_changed,
+ };
++#endif
+ 
+ static int
+ weston_pipewire_init(struct weston_pipewire *pipewire)
+@@ -745,10 +849,19 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
+ 
+ 	pw_loop_enter(pipewire->loop);
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	pipewire->context = pw_context_new(pipewire->loop, NULL, 0);
++#else
+ 	pipewire->core = pw_core_new(pipewire->loop, NULL);
+ 	pipewire->t = pw_core_get_type(pipewire->core);
+ 	init_type(&pipewire->type, pipewire->t->map);
++#endif
+ 
++#if PW_CHECK_VERSION(0, 2, 90)
++	pw_core_add_listener(pipewire->core,
++			       &pipewire->core_listener,
++			       &core_events, pipewire);
++#else
+ 	pipewire->remote = pw_remote_new(pipewire->core, NULL, 0);
+ 	pw_remote_add_listener(pipewire->remote,
+ 			       &pipewire->remote_listener,
+@@ -777,6 +890,7 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
+ 			goto err;
+ 		}
+ 	}
++#endif
+ 
+ 	loop = wl_display_get_event_loop(pipewire->compositor->wl_display);
+ 	pipewire->loop_source =
+@@ -786,12 +900,14 @@ weston_pipewire_init(struct weston_pipewire *pipewire)
+ 				     pipewire);
+ 
+ 	return 0;
++#if !PW_CHECK_VERSION(0, 2, 90)
+ err:
+ 	if (pipewire->remote)
+ 		pw_remote_destroy(pipewire->remote);
+ 	pw_loop_leave(pipewire->loop);
+ 	pw_loop_destroy(pipewire->loop);
+ 	return -1;
++#endif
+ }
+ 
+ static const struct weston_pipewire_api pipewire_api = {
+-- 
+2.25.1
+