Implement server-side resizing
parent
eb4b9d71a4
commit
a0801f04e4
|
@ -78,6 +78,8 @@ struct nvnc_client {
|
||||||
size_t buffer_index;
|
size_t buffer_index;
|
||||||
size_t buffer_len;
|
size_t buffer_len;
|
||||||
uint8_t msg_buffer[MSG_BUFFER_SIZE];
|
uint8_t msg_buffer[MSG_BUFFER_SIZE];
|
||||||
|
uint32_t known_width;
|
||||||
|
uint32_t known_height;
|
||||||
};
|
};
|
||||||
|
|
||||||
LIST_HEAD(nvnc_client_list, nvnc_client);
|
LIST_HEAD(nvnc_client_list, nvnc_client);
|
||||||
|
|
49
src/server.c
49
src/server.c
|
@ -384,6 +384,8 @@ static void send_server_init_message(struct nvnc_client* client)
|
||||||
struct rcbuf* payload = rcbuf_new(msg, size);
|
struct rcbuf* payload = rcbuf_new(msg, size);
|
||||||
stream_send(client->net_stream, payload, NULL, NULL);
|
stream_send(client->net_stream, payload, NULL, NULL);
|
||||||
|
|
||||||
|
client->known_width = width;
|
||||||
|
client->known_height = height;
|
||||||
return;
|
return;
|
||||||
|
|
||||||
pixfmt_failure:
|
pixfmt_failure:
|
||||||
|
@ -963,6 +965,16 @@ static enum tight_quality client_get_tight_quality(struct nvnc_client* client)
|
||||||
return TIGHT_QUALITY_LOSSLESS;
|
return TIGHT_QUALITY_LOSSLESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool client_has_encoding(const struct nvnc_client* client,
|
||||||
|
enum rfb_encodings encoding)
|
||||||
|
{
|
||||||
|
for (size_t i = 0; i < client->n_encodings; ++i)
|
||||||
|
if (client->encodings[i] == encoding)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
static void do_client_update_fb(void* work)
|
static void do_client_update_fb(void* work)
|
||||||
{
|
{
|
||||||
struct fb_update_work* update = aml_get_userdata(work);
|
struct fb_update_work* update = aml_get_userdata(work);
|
||||||
|
@ -1028,6 +1040,37 @@ static void on_client_update_fb_done(void* work)
|
||||||
client_unref(client);
|
client_unref(client);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int send_desktop_resize(struct nvnc_client* client, struct nvnc_fb* fb)
|
||||||
|
{
|
||||||
|
if (!client_has_encoding(client, RFB_ENCODING_DESKTOPSIZE)) {
|
||||||
|
log_error("Client does not support desktop resizing. Closing connection...\n");
|
||||||
|
stream_close(client->net_stream);
|
||||||
|
client_unref(client);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
client->known_width = fb->width;
|
||||||
|
client->known_height = fb->height;
|
||||||
|
|
||||||
|
pixman_region_union_rect(&client->damage, &client->damage, 0, 0,
|
||||||
|
fb->width, fb->height);
|
||||||
|
|
||||||
|
struct rfb_server_fb_update_msg head = {
|
||||||
|
.type = RFB_SERVER_TO_CLIENT_FRAMEBUFFER_UPDATE,
|
||||||
|
.n_rects = htons(1),
|
||||||
|
};
|
||||||
|
|
||||||
|
struct rfb_server_fb_rect rect = {
|
||||||
|
.encoding = htonl(RFB_ENCODING_DESKTOPSIZE),
|
||||||
|
.width = htons(fb->width),
|
||||||
|
.height = htons(fb->height),
|
||||||
|
};
|
||||||
|
|
||||||
|
stream_write(client->net_stream, &head, sizeof(head), NULL, NULL);
|
||||||
|
stream_write(client->net_stream, &rect, sizeof(rect), NULL, NULL);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
int schedule_client_update_fb(struct nvnc_client* client)
|
int schedule_client_update_fb(struct nvnc_client* client)
|
||||||
{
|
{
|
||||||
struct nvnc_fb* fb = client->server->display->buffer;
|
struct nvnc_fb* fb = client->server->display->buffer;
|
||||||
|
@ -1045,6 +1088,11 @@ int schedule_client_update_fb(struct nvnc_client* client)
|
||||||
work->client = client;
|
work->client = client;
|
||||||
work->fb = fb;
|
work->fb = fb;
|
||||||
|
|
||||||
|
if (fb->width != client->known_width
|
||||||
|
|| fb->height != client->known_height)
|
||||||
|
if (send_desktop_resize(client, fb) < 0)
|
||||||
|
goto resize_failure;
|
||||||
|
|
||||||
/* The client's damage is exchanged for an empty one */
|
/* The client's damage is exchanged for an empty one */
|
||||||
work->region = client->damage;
|
work->region = client->damage;
|
||||||
pixman_region_init(&client->damage);
|
pixman_region_init(&client->damage);
|
||||||
|
@ -1080,6 +1128,7 @@ oom_failure:
|
||||||
vec_destroy(&work->frame);
|
vec_destroy(&work->frame);
|
||||||
vec_failure:
|
vec_failure:
|
||||||
pixfmt_failure:
|
pixfmt_failure:
|
||||||
|
resize_failure:
|
||||||
free(work);
|
free(work);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue