gnome-remote-desktop/SOURCES/rhel8.0.0-backports.patch
2021-10-08 11:27:39 +00:00

720 lines
24 KiB
Diff

From b9221b1efcfe205409628bf365008e0b248725f3 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jonas=20=C3=85dahl?= <jadahl@gmail.com>
Date: Fri, 23 Nov 2018 16:55:20 +0100
Subject: [PATCH 1/6] vnc: Detach source when client is gone
LibVNCServer will close the socket for us, so don't keep the socket
source attached after a client is gone. It's not fast enough to close it
in the idle function, as that means we'd get a G_IO_NVAL error when the
source is processed.
Fixes: https://gitlab.gnome.org/jadahl/gnome-remote-desktop/issues/23
---
src/grd-session-vnc.c | 1 +
1 file changed, 1 insertion(+)
diff --git a/src/grd-session-vnc.c b/src/grd-session-vnc.c
index 3c98eeb..fbf41e2 100644
--- a/src/grd-session-vnc.c
+++ b/src/grd-session-vnc.c
@@ -182,6 +182,7 @@ handle_client_gone (rfbClientPtr rfb_client)
g_debug ("VNC client gone");
+ grd_session_vnc_detach_source (session_vnc);
maybe_queue_close_session_idle (session_vnc);
}
--
2.19.1
From 5ce2a1a6f80581d7d5b79b3a86f6707d22ad94ba Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jonas=20=C3=85dahl?= <jadahl@gmail.com>
Date: Mon, 26 Nov 2018 16:37:12 +0100
Subject: [PATCH 2/6] session/vnc: Always set pixel format translate functions
Internally LibVNCServer uses RGBX, but we provide BGRX. Currently the
LibVNCServer API doesn't allow to override this, but internally, it
supports any order of the color components. We relied on this already,
to avoid an extra pixel conversion, but we failed to update the
conversion table.
Fixes: https://gitlab.gnome.org/jadahl/gnome-remote-desktop/issues/20
---
src/grd-session-vnc.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/src/grd-session-vnc.c b/src/grd-session-vnc.c
index fbf41e2..c6be742 100644
--- a/src/grd-session-vnc.c
+++ b/src/grd-session-vnc.c
@@ -115,11 +115,13 @@ resize_vnc_framebuffer (GrdSessionVnc *session_vnc,
BGRX_BYTES_PER_PIXEL);
/*
- * Our format is hard coded to BGRX but LibVNCServer asusumes it's RGBX;
+ * Our format is hard coded to BGRX but LibVNCServer assumes it's RGBX;
* lets override that.
*/
+
swap_uint8 (&session_vnc->rfb_screen->serverFormat.redShift,
&session_vnc->rfb_screen->serverFormat.blueShift);
+ rfb_screen->setTranslateFunction (session_vnc->rfb_client);
}
void
--
2.19.1
From b3bb9ebb47a9883c1022a1ad3dc90aa9bb9c2d27 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jonas=20=C3=85dahl?= <jadahl@gmail.com>
Date: Mon, 17 Dec 2018 13:12:38 +0100
Subject: [PATCH 3/6] session/vnc: Update server format earlier too
We update the server protocol to swap the blue and red shift levels, as
LibVNCServer only RGBX by default, but we pass BGRX. Doing this just
after resizing the framebuffer where the format is updated is too late
though, as for some reason LibVNCServer's tight encoding still gets it
wrong when encoding JPEG rects.
Fixes: https://gitlab.gnome.org/jadahl/gnome-remote-desktop/issues/20
---
src/grd-session-vnc.c | 22 +++++++++++++++-------
1 file changed, 15 insertions(+), 7 deletions(-)
diff --git a/src/grd-session-vnc.c b/src/grd-session-vnc.c
index c6be742..b86c3a7 100644
--- a/src/grd-session-vnc.c
+++ b/src/grd-session-vnc.c
@@ -94,6 +94,19 @@ swap_uint8 (uint8_t *a,
*b = tmp;
}
+static void
+update_server_format (GrdSessionVnc *session_vnc)
+{
+ rfbScreenInfoPtr rfb_screen = session_vnc->rfb_screen;
+
+ /*
+ * Our format is hard coded to BGRX but LibVNCServer assumes it's RGBX;
+ * lets override that.
+ */
+ swap_uint8 (&rfb_screen->serverFormat.redShift,
+ &rfb_screen->serverFormat.blueShift);
+}
+
static void
resize_vnc_framebuffer (GrdSessionVnc *session_vnc,
int width,
@@ -114,13 +127,7 @@ resize_vnc_framebuffer (GrdSessionVnc *session_vnc,
BGRX_SAMPLES_PER_PIXEL,
BGRX_BYTES_PER_PIXEL);
- /*
- * Our format is hard coded to BGRX but LibVNCServer assumes it's RGBX;
- * lets override that.
- */
-
- swap_uint8 (&session_vnc->rfb_screen->serverFormat.redShift,
- &session_vnc->rfb_screen->serverFormat.blueShift);
+ update_server_format (session_vnc);
rfb_screen->setTranslateFunction (session_vnc->rfb_client);
}
@@ -517,6 +524,7 @@ init_vnc_session (GrdSessionVnc *session_vnc)
rfb_screen = rfbGetScreen (0, NULL,
screen_width, screen_height,
8, 3, 4);
+ update_server_format (session_vnc);
socket = g_socket_connection_get_socket (session_vnc->connection);
rfb_screen->inetdSock = g_socket_get_fd (socket);
--
2.19.1
From 930d1c127e4a2252e3288cd3c752debe88d938c4 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jonas=20=C3=85dahl?= <jadahl@gmail.com>
Date: Mon, 17 Dec 2018 14:35:17 +0100
Subject: [PATCH 4/6] vnc: Request cursor sprite as PipeWire metadata
This allows sending cursor updates, including position and cursor
sprite, without having to embed it into the framebuffer. In effect, when
there is a hardware cursor in the compositor, moving the cursor will not
result in any actual frames being copied.
The actual cursor sprite sent over VNC is derived from the cursor sprite
used in the compositor. The conversion is lossy, as the VNC cursor
sprite is a 3 bits per pixel (transparen, white or black), and the cursor
sprite from the compositor is 32 bits per pixel.
This bumps the PipeWire requirement to 0.2.5.
---
meson.build | 2 +-
src/grd-session-vnc.c | 24 +++++++
src/grd-session-vnc.h | 7 ++
src/grd-session.c | 10 +++
src/grd-types.h | 5 ++
src/grd-vnc-cursor.c | 125 ++++++++++++++++++++++++++++++++++
src/grd-vnc-cursor.h | 37 ++++++++++
src/grd-vnc-pipewire-stream.c | 94 +++++++++++++++++++++++--
src/meson.build | 2 +
9 files changed, 299 insertions(+), 7 deletions(-)
create mode 100644 src/grd-vnc-cursor.c
create mode 100644 src/grd-vnc-cursor.h
diff --git a/meson.build b/meson.build
index cb0d5fe..b6bfb6f 100644
--- a/meson.build
+++ b/meson.build
@@ -10,7 +10,7 @@ gnome = import('gnome')
glib_dep = dependency('glib-2.0')
gio_dep = dependency('gio-2.0')
gio_unix_dep = dependency('gio-unix-2.0')
-pipewire_dep = dependency('libpipewire-0.2', version: '>= 0.2.2')
+pipewire_dep = dependency('libpipewire-0.2', version: '>= 0.2.5')
systemd_dep = dependency('systemd')
libvncserver_dep = dependency('libvncserver')
libsecret_dep = dependency('libsecret-1')
diff --git a/src/grd-session-vnc.c b/src/grd-session-vnc.c
index b86c3a7..247c130 100644
--- a/src/grd-session-vnc.c
+++ b/src/grd-session-vnc.c
@@ -174,6 +174,30 @@ grd_session_vnc_draw_buffer (GrdSessionVnc *session_vnc,
rfbProcessEvents (session_vnc->rfb_screen, 0);
}
+void
+grd_session_vnc_set_cursor (GrdSessionVnc *session_vnc,
+ rfbCursorPtr rfb_cursor)
+{
+ rfbSetCursor (session_vnc->rfb_screen, rfb_cursor);
+}
+
+void
+grd_session_vnc_move_cursor (GrdSessionVnc *session_vnc,
+ int x,
+ int y)
+{
+ if (session_vnc->rfb_screen->cursorX == x ||
+ session_vnc->rfb_screen->cursorY == y)
+ return;
+
+ LOCK (session_vnc->rfb_screen->cursorMutex);
+ session_vnc->rfb_screen->cursorX = x;
+ session_vnc->rfb_screen->cursorY = y;
+ UNLOCK (session_vnc->rfb_screen->cursorMutex);
+
+ session_vnc->rfb_client->cursorWasMoved = TRUE;
+}
+
static void
maybe_queue_close_session_idle (GrdSessionVnc *session_vnc)
{
diff --git a/src/grd-session-vnc.h b/src/grd-session-vnc.h
index 33245bc..789693e 100644
--- a/src/grd-session-vnc.h
+++ b/src/grd-session-vnc.h
@@ -51,6 +51,13 @@ void grd_session_vnc_draw_buffer (GrdSessionVnc *session_vnc,
int grd_session_vnc_get_fd (GrdSessionVnc *session_vnc);
+void grd_session_vnc_set_cursor (GrdSessionVnc *session_vnc,
+ rfbCursorPtr rfb_cursor);
+
+void grd_session_vnc_move_cursor (GrdSessionVnc *session_vnc,
+ int x,
+ int y);
+
int grd_session_vnc_get_framebuffer_stride (GrdSessionVnc *session_vnc);
rfbClientPtr grd_session_vnc_get_rfb_client (GrdSessionVnc *session_vnc);
diff --git a/src/grd-session.c b/src/grd-session.c
index 212770b..3697584 100644
--- a/src/grd-session.c
+++ b/src/grd-session.c
@@ -47,6 +47,13 @@ enum
static guint signals[LAST_SIGNAL];
+typedef enum _GrdScreenCastCursorMode
+{
+ GRD_SCREEN_CAST_CURSOR_MODE_HIDDEN = 0,
+ GRD_SCREEN_CAST_CURSOR_MODE_EMBEDDED = 1,
+ GRD_SCREEN_CAST_CURSOR_MODE_METADATA = 2,
+} GrdScreenCastCursorMode;
+
typedef struct _GrdSessionPrivate
{
GrdContext *context;
@@ -296,6 +303,9 @@ on_screen_cast_session_proxy_acquired (GObject *object,
priv->screen_cast_session = session_proxy;
g_variant_builder_init (&properties_builder, G_VARIANT_TYPE ("a{sv}"));
+ g_variant_builder_add (&properties_builder, "{sv}",
+ "cursor-mode",
+ g_variant_new_uint32 (GRD_SCREEN_CAST_CURSOR_MODE_METADATA));
/* TODO: Support something other than primary monitor */
grd_dbus_screen_cast_session_call_record_monitor (session_proxy,
diff --git a/src/grd-types.h b/src/grd-types.h
index af92c88..89dd22f 100644
--- a/src/grd-types.h
+++ b/src/grd-types.h
@@ -31,4 +31,9 @@ typedef struct _GrdPipeWireStream GrdPipeWireStream;
typedef struct _GrdPipeWireStreamMonitor GrdPipeWireStreamMonitor;
typedef struct _GrdVncServer GrdVncServer;
+typedef enum _GrdPixelFormat
+{
+ GRD_PIXEL_FORMAT_RGBA8888,
+} GrdPixelFormat;
+
#endif /* GRD_TYPES_H */
diff --git a/src/grd-vnc-cursor.c b/src/grd-vnc-cursor.c
new file mode 100644
index 0000000..c0cb1aa
--- /dev/null
+++ b/src/grd-vnc-cursor.c
@@ -0,0 +1,125 @@
+/*
+ * Copyright (C) 2018 Red Hat Inc.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ *
+ */
+
+#include "config.h"
+
+#include "grd-vnc-cursor.h"
+
+#include <glib.h>
+#include <stdint.h>
+
+static void
+get_pixel_components (uint32_t pixel,
+ GrdPixelFormat format,
+ uint8_t *a,
+ uint8_t *r,
+ uint8_t *g,
+ uint8_t *b)
+{
+ g_assert (format == GRD_PIXEL_FORMAT_RGBA8888);
+
+ *a = (pixel & 0xff000000) >> 24;
+ *b = (pixel & 0xff0000) >> 16;
+ *g = (pixel & 0xff00) >> 8;
+ *r = pixel & 0xff;
+}
+
+static gboolean
+is_practically_black (uint8_t r,
+ uint8_t g,
+ uint8_t b)
+{
+ if (r <= 0x62 &&
+ g <= 0x62 &&
+ b <= 0x62)
+ return TRUE;
+ else
+ return FALSE;
+}
+
+static gboolean
+is_practically_opaque (uint8_t a)
+{
+ return a > 0xe0;
+}
+
+rfbCursorPtr
+grd_vnc_create_cursor (int width,
+ int height,
+ int stride,
+ GrdPixelFormat format,
+ uint8_t *buf)
+{
+ g_autofree char *cursor = NULL;
+ g_autofree char *mask = NULL;
+ int y;
+
+ g_return_val_if_fail (format == GRD_PIXEL_FORMAT_RGBA8888, NULL);
+
+ cursor = g_new0 (char, width * height);
+ mask = g_new0 (char, width * height);
+
+ for (y = 0; y < height; y++)
+ {
+ uint32_t *pixel_row;
+ int x;
+
+ pixel_row = (uint32_t *) &buf[y * stride];
+
+ for (x = 0; x < width; x++)
+ {
+ uint32_t pixel = pixel_row[x];
+ uint8_t a, r, g, b;
+
+ get_pixel_components (pixel,
+ format,
+ &a, &r, &g, &b);
+
+ if (is_practically_opaque (a))
+ {
+ if (is_practically_black (r, g, b))
+ cursor[y * width + x] = ' ';
+ else
+ cursor[y * width + x] = 'x';
+
+ mask[y * width + x] = 'x';
+ }
+ else
+ {
+ cursor[y * width + x] = ' ';
+ mask[y * width + x] = ' ';
+ }
+ }
+ }
+
+ return rfbMakeXCursor (width, height, cursor, mask);
+}
+
+rfbCursorPtr
+grd_vnc_create_empty_cursor (int width,
+ int height)
+{
+ g_autofree char *cursor = NULL;
+ cursor = g_new0 (char, width * height);
+
+ memset (cursor, ' ', width * height);
+
+ return rfbMakeXCursor (width, height, cursor, cursor);
+}
diff --git a/src/grd-vnc-cursor.h b/src/grd-vnc-cursor.h
new file mode 100644
index 0000000..36bd0fb
--- /dev/null
+++ b/src/grd-vnc-cursor.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2018 Red Hat Inc.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ *
+ */
+
+#ifndef GRD_VNC_CURSOR_H
+#define GRD_VNC_CURSOR_H
+
+#include <rfb/rfb.h>
+
+#include "grd-types.h"
+
+rfbCursorPtr grd_vnc_create_cursor (int width,
+ int height,
+ int stride,
+ GrdPixelFormat format,
+ uint8_t *buf);
+
+rfbCursorPtr grd_vnc_create_empty_cursor (int width,
+ int height);
+
+#endif /* GRD_VNC_CURSOR_H */
diff --git a/src/grd-vnc-pipewire-stream.c b/src/grd-vnc-pipewire-stream.c
index d6454b8..c341887 100644
--- a/src/grd-vnc-pipewire-stream.c
+++ b/src/grd-vnc-pipewire-stream.c
@@ -28,6 +28,8 @@
#include <spa/param/video/format-utils.h>
#include <sys/mman.h>
+#include "grd-vnc-cursor.h"
+
enum
{
CLOSED,
@@ -43,6 +45,7 @@ typedef struct _GrdSpaType
struct spa_type_media_subtype media_subtype;
struct spa_type_format_video format_video;
struct spa_type_video_format video_format;
+ uint32_t meta_cursor;
} GrdSpaType;
typedef struct _GrdPipeWireSource
@@ -79,6 +82,11 @@ struct _GrdVncPipeWireStream
G_DEFINE_TYPE (GrdVncPipeWireStream, grd_vnc_pipewire_stream,
G_TYPE_OBJECT)
+#define CURSOR_META_SIZE(width, height) \
+ (sizeof(struct spa_meta_cursor) + \
+ sizeof(struct spa_meta_bitmap) + width * height * 4)
+
+
static void
init_spa_type (GrdSpaType *type,
struct spa_type_map *map)
@@ -87,6 +95,7 @@ init_spa_type (GrdSpaType *type,
spa_type_media_subtype_map (map, &type->media_subtype);
spa_type_format_video_map (map, &type->format_video);
spa_type_video_format_map (map, &type->video_format);
+ type->meta_cursor = spa_type_map_get_id (map, SPA_TYPE_META__Cursor);
}
static gboolean
@@ -196,7 +205,7 @@ on_stream_format_changed (void *user_data,
int height;
int stride;
int size;
- const struct spa_pod *params[2];
+ const struct spa_pod *params[3];
if (!format)
{
@@ -231,7 +240,29 @@ on_stream_format_changed (void *user_data,
":", pipewire_type->param_meta.type, "I", pipewire_type->meta.Header,
":", pipewire_type->param_meta.size, "i", sizeof(struct spa_meta_header));
- pw_stream_finish_format (stream->pipewire_stream, 0, params, 2);
+ params[2] = spa_pod_builder_object(
+ &pod_builder,
+ pipewire_type->param.idMeta, pipewire_type->param_meta.Meta,
+ ":", pipewire_type->param_meta.type, "I", stream->spa_type.meta_cursor,
+ ":", pipewire_type->param_meta.size, "iru", CURSOR_META_SIZE (64,64),
+ SPA_POD_PROP_MIN_MAX (CURSOR_META_SIZE (1,1),
+ CURSOR_META_SIZE (256,256)));
+
+ pw_stream_finish_format (stream->pipewire_stream, 0,
+ params, G_N_ELEMENTS (params));
+}
+
+static gboolean
+spa_pixel_format_to_grd_pixel_format (GrdSpaType *spa_type,
+ uint32_t spa_format,
+ GrdPixelFormat *out_format)
+{
+ if (spa_format == spa_type->video_format.RGBA)
+ *out_format = GRD_PIXEL_FORMAT_RGBA8888;
+ else
+ return FALSE;
+
+ return TRUE;
}
static int
@@ -243,12 +274,19 @@ do_render (struct spa_loop *loop,
void *user_data)
{
GrdVncPipeWireStream *stream = GRD_VNC_PIPEWIRE_STREAM (user_data);
+ GrdSpaType *spa_type = &stream->spa_type;
struct spa_buffer *buffer = ((struct spa_buffer **) data)[0];
uint8_t *map;
void *src_data;
+ struct spa_meta_cursor *spa_meta_cursor;
- if (buffer->datas[0].type == stream->pipewire_type->data.MemFd ||
- buffer->datas[0].type == stream->pipewire_type->data.DmaBuf)
+ if (buffer->datas[0].chunk->size == 0)
+ {
+ map = NULL;
+ src_data = NULL;
+ }
+ else if (buffer->datas[0].type == stream->pipewire_type->data.MemFd ||
+ buffer->datas[0].type == stream->pipewire_type->data.DmaBuf)
{
map = mmap (NULL, buffer->datas[0].maxsize + buffer->datas[0].mapoffset,
PROT_READ, MAP_PRIVATE, buffer->datas[0].fd, 0);
@@ -264,7 +302,51 @@ do_render (struct spa_loop *loop,
return -EINVAL;
}
- grd_session_vnc_draw_buffer (stream->session, src_data);
+ spa_meta_cursor = spa_buffer_find_meta (buffer, spa_type->meta_cursor);
+ if (spa_meta_cursor && spa_meta_cursor_is_valid (spa_meta_cursor))
+ {
+ struct spa_meta_bitmap *spa_meta_bitmap;
+ GrdPixelFormat format;
+
+ spa_meta_bitmap = SPA_MEMBER (spa_meta_cursor,
+ spa_meta_cursor->bitmap_offset,
+ struct spa_meta_bitmap);
+
+ if (spa_meta_bitmap->size.width > 0 &&
+ spa_meta_bitmap->size.height > 0 &&
+ spa_pixel_format_to_grd_pixel_format (spa_type,
+ spa_meta_bitmap->format,
+ &format))
+ {
+ uint8_t *buf;
+ rfbCursorPtr rfb_cursor;
+
+ buf = SPA_MEMBER (spa_meta_bitmap, spa_meta_bitmap->offset, uint8_t);
+ rfb_cursor = grd_vnc_create_cursor (spa_meta_bitmap->size.width,
+ spa_meta_bitmap->size.height,
+ spa_meta_bitmap->stride,
+ format,
+ buf);
+ rfb_cursor->xhot = spa_meta_cursor->hotspot.x;
+ rfb_cursor->yhot = spa_meta_cursor->hotspot.y;
+
+ grd_session_vnc_set_cursor (stream->session, rfb_cursor);
+ }
+ else
+ {
+ rfbCursorPtr empty_cursor;
+
+ empty_cursor = grd_vnc_create_empty_cursor (1, 1);
+ grd_session_vnc_set_cursor (stream->session, empty_cursor);
+ }
+
+ grd_session_vnc_move_cursor (stream->session,
+ spa_meta_cursor->position.x,
+ spa_meta_cursor->position.y);
+ }
+
+ if (src_data)
+ grd_session_vnc_draw_buffer (stream->session, src_data);
if (map)
munmap (map, buffer->datas[0].maxsize + buffer->datas[0].mapoffset);
@@ -306,7 +388,7 @@ connect_to_stream (GrdVncPipeWireStream *stream,
struct spa_rectangle max_rect;
struct spa_fraction min_framerate;
struct spa_fraction max_framerate;
- const struct spa_pod *params[1];
+ const struct spa_pod *params[2];
int ret;
pipewire_stream = pw_stream_new (stream->pipewire_remote,
diff --git a/src/meson.build b/src/meson.build
index b633ad7..31c7221 100644
--- a/src/meson.build
+++ b/src/meson.build
@@ -15,6 +15,8 @@ daemon_sources = files([
'grd-stream.c',
'grd-stream.h',
'grd-types.h',
+ 'grd-vnc-cursor.c',
+ 'grd-vnc-cursor.h',
'grd-vnc-pipewire-stream.c',
'grd-vnc-pipewire-stream.h',
'grd-vnc-server.c',
--
2.19.1
From 6aff333ef474abfe18e0da964032e08e6cda2cd6 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jonas=20=C3=85dahl?= <jadahl@gmail.com>
Date: Thu, 3 Jan 2019 18:07:33 +0100
Subject: [PATCH 5/6] session/vnc: Set rfbScreenPtr pointer earlier
Otherwise the format update_server_format() function doesn't find it.
---
src/grd-session-vnc.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/grd-session-vnc.c b/src/grd-session-vnc.c
index 247c130..dcd8599 100644
--- a/src/grd-session-vnc.c
+++ b/src/grd-session-vnc.c
@@ -548,6 +548,8 @@ init_vnc_session (GrdSessionVnc *session_vnc)
rfb_screen = rfbGetScreen (0, NULL,
screen_width, screen_height,
8, 3, 4);
+ session_vnc->rfb_screen = rfb_screen;
+
update_server_format (session_vnc);
socket = g_socket_connection_get_socket (session_vnc->connection);
@@ -567,8 +569,6 @@ init_vnc_session (GrdSessionVnc *session_vnc)
rfb_screen->frameBuffer = g_malloc0 (screen_width * screen_height * 4);
memset (rfb_screen->frameBuffer, 0x1f, screen_width * screen_height * 4);
- session_vnc->rfb_screen = rfb_screen;
-
rfbInitServer (rfb_screen);
rfbProcessEvents (rfb_screen, 0);
}
--
2.19.1
From 5d9ffd0efe8b32d95c1a566f431e7d14fa95f3fa Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jonas=20=C3=85dahl?= <jadahl@gmail.com>
Date: Thu, 3 Jan 2019 18:08:52 +0100
Subject: [PATCH 6/6] vnc-pipewire-stream: Assume no bitmap offset means no
bitmap change
This is according to the agreed semantics:
https://github.com/PipeWire/pipewire/commit/8984c6f48d2106f143d3f6d5df976f788ecfde30
---
src/grd-vnc-pipewire-stream.c | 18 +++++++++++++-----
1 file changed, 13 insertions(+), 5 deletions(-)
diff --git a/src/grd-vnc-pipewire-stream.c b/src/grd-vnc-pipewire-stream.c
index c341887..cee569a 100644
--- a/src/grd-vnc-pipewire-stream.c
+++ b/src/grd-vnc-pipewire-stream.c
@@ -308,11 +308,19 @@ do_render (struct spa_loop *loop,
struct spa_meta_bitmap *spa_meta_bitmap;
GrdPixelFormat format;
- spa_meta_bitmap = SPA_MEMBER (spa_meta_cursor,
- spa_meta_cursor->bitmap_offset,
- struct spa_meta_bitmap);
+ if (spa_meta_cursor->bitmap_offset)
+ {
+ spa_meta_bitmap = SPA_MEMBER (spa_meta_cursor,
+ spa_meta_cursor->bitmap_offset,
+ struct spa_meta_bitmap);
+ }
+ else
+ {
+ spa_meta_bitmap = NULL;
+ }
- if (spa_meta_bitmap->size.width > 0 &&
+ if (spa_meta_bitmap &&
+ spa_meta_bitmap->size.width > 0 &&
spa_meta_bitmap->size.height > 0 &&
spa_pixel_format_to_grd_pixel_format (spa_type,
spa_meta_bitmap->format,
@@ -332,7 +340,7 @@ do_render (struct spa_loop *loop,
grd_session_vnc_set_cursor (stream->session, rfb_cursor);
}
- else
+ else if (spa_meta_bitmap)
{
rfbCursorPtr empty_cursor;
--
2.19.1