[Spice-devel] [PATCH spice-gtk 05/10] display: keep a reference to the primary surface
Yonit Halperin
yhalperi at redhat.com
Mon Sep 9 13:26:41 PDT 2013
ack
On 09/08/2013 02:59 PM, Marc-André Lureau wrote:
> Avoid hard-coding surface 0 as being primary, although in practice it
> always is so far. Also a lot of lookups are primary, so add a shortcut
> for this special case (~30% apparently), it shows some small lookup
> speedup.
>
> before:
> real 0m5.008s
> user 0m3.253s
> sys 0m2.015s
>
> after:
> real 0m4.930s
> user 0m3.133s
> sys 0m2.027s
> ---
> gtk/channel-display.c | 28 +++++++++++++++-------------
> 1 file changed, 15 insertions(+), 13 deletions(-)
>
> diff --git a/gtk/channel-display.c b/gtk/channel-display.c
> index 979ce7b..03ae535 100644
> --- a/gtk/channel-display.c
> +++ b/gtk/channel-display.c
> @@ -67,6 +67,7 @@
>
> struct _SpiceDisplayChannelPrivate {
> GHashTable *surfaces;
> + display_surface *primary;
> display_cache *images;
> display_cache *palettes;
> SpiceImageCache image_cache;
> @@ -180,13 +181,11 @@ static void spice_display_get_property(GObject *object,
>
> switch (prop_id) {
> case PROP_WIDTH: {
> - display_surface *surface = find_surface(c, 0);
> - g_value_set_uint(value, surface ? surface->width : 0);
> + g_value_set_uint(value, c->primary ? c->primary->width : 0);
> break;
> }
> case PROP_HEIGHT: {
> - display_surface *surface = find_surface(c, 0);
> - g_value_set_uint(value, surface ? surface->height : 0);
> + g_value_set_uint(value, c->primary ? c->primary->height : 0);
> break;
> }
> case PROP_MONITORS: {
> @@ -739,18 +738,16 @@ static int create_canvas(SpiceChannel *channel, display_surface *surface)
> SpiceDisplayChannelPrivate *c = SPICE_DISPLAY_CHANNEL(channel)->priv;
>
> if (surface->primary) {
> - display_surface *primary = find_surface(c, 0);
> -
> - if (primary) {
> - if (primary->width == surface->width &&
> - primary->height == surface->height) {
> + if (c->primary) {
> + if (c->primary->width == surface->width &&
> + c->primary->height == surface->height) {
> CHANNEL_DEBUG(channel, "Reusing existing primary surface");
> return 0;
> }
>
> emit_main_context(channel, SPICE_DISPLAY_PRIMARY_DESTROY);
>
> - g_hash_table_remove(c->surfaces, 0);
> + g_hash_table_remove(c->surfaces, GINT_TO_POINTER(c->primary->surface_id));
> }
>
> CHANNEL_DEBUG(channel, "Create primary canvas");
> @@ -803,6 +800,8 @@ static int create_canvas(SpiceChannel *channel, display_surface *surface)
> g_hash_table_insert(c->surfaces, GINT_TO_POINTER(surface->surface_id), surface);
>
> if (surface->primary) {
> + g_warn_if_fail(c->primary == NULL);
> + c->primary = surface;
> emit_main_context(channel, SPICE_DISPLAY_PRIMARY_CREATE,
> surface->format, surface->width, surface->height,
> surface->stride, surface->shmid, surface->data);
> @@ -847,6 +846,9 @@ static void destroy_canvas(display_surface *surface)
>
> static display_surface *find_surface(SpiceDisplayChannelPrivate *c, guint32 surface_id)
> {
> + if (c->primary && c->primary->surface_id == surface_id)
> + return c->primary;
> +
> return g_hash_table_lookup(c->surfaces, GINT_TO_POINTER(surface_id));
> }
>
> @@ -944,10 +946,9 @@ static void display_handle_mode(SpiceChannel *channel, SpiceMsgIn *in)
> static void display_handle_mark(SpiceChannel *channel, SpiceMsgIn *in)
> {
> SpiceDisplayChannelPrivate *c = SPICE_DISPLAY_CHANNEL(channel)->priv;
> - display_surface *surface = find_surface(c, 0);
>
> CHANNEL_DEBUG(channel, "%s", __FUNCTION__);
> - g_return_if_fail(surface != NULL);
> + g_return_if_fail(c->primary != NULL);
> #ifdef EXTRA_CHECKS
> g_warn_if_fail(c->mark == FALSE);
> #endif
> @@ -960,7 +961,7 @@ static void display_handle_mark(SpiceChannel *channel, SpiceMsgIn *in)
> static void display_handle_reset(SpiceChannel *channel, SpiceMsgIn *in)
> {
> SpiceDisplayChannelPrivate *c = SPICE_DISPLAY_CHANNEL(channel)->priv;
> - display_surface *surface = find_surface(c, 0);
> + display_surface *surface = c->primary;
>
> CHANNEL_DEBUG(channel, "%s: TODO detach_from_screen", __FUNCTION__);
>
> @@ -1784,6 +1785,7 @@ static void display_handle_surface_destroy(SpiceChannel *channel, SpiceMsgIn *in
> if (id != 0 && c->mark_false_event_id == 0) {
> c->mark_false_event_id = g_timeout_add_seconds(1, display_mark_false, channel);
> }
> + c->primary = NULL;
> emit_main_context(channel, SPICE_DISPLAY_PRIMARY_DESTROY);
> }
>
>
More information about the Spice-devel
mailing list