display: use prefixed display names for cache lookups.
authorGwenole Beauchesne <gwenole.beauchesne@intel.com>
Tue, 24 Jul 2012 17:43:40 +0000 (19:43 +0200)
committerGwenole Beauchesne <gwenole.beauchesne@intel.com>
Wed, 25 Jul 2012 12:27:05 +0000 (14:27 +0200)
This improves display name comparisons by always allocating a valid display
name. This also helps to disambiguate lookups by name in the global display
cache, should a new backend be implemented.

gst-libs/gst/vaapi/gstvaapidisplay_x11.c

index 0f5f7ba..6ad5ed1 100644 (file)
@@ -48,6 +48,15 @@ enum {
     PROP_X11_SCREEN
 };
 
+#define NAME_PREFIX "X11:"
+#define NAME_PREFIX_LENGTH 4
+
+static inline gboolean
+is_display_name(const gchar *display_name)
+{
+    return strncmp(display_name, NAME_PREFIX, NAME_PREFIX_LENGTH) == 0;
+}
+
 static inline const gchar *
 get_default_display_name(void)
 {
@@ -61,25 +70,35 @@ get_default_display_name(void)
 static gboolean
 compare_display_name(gconstpointer a, gconstpointer b, gpointer user_data)
 {
-    const gchar *display_name;
+    const gchar *cached_name = a, *cached_name_end;
+    const gchar *tested_name = b, *tested_name_end;
+    guint cached_name_length, tested_name_length;
 
-    /* XXX: handle screen number? */
-    if (a && b)
-        return strcmp(a, b) == 0;
-
-    /* Match "" or default display name */
-    if (a)
-        display_name = a;
-    else if (b)
-        display_name = b;
+    if (!cached_name || !is_display_name(cached_name))
+        return FALSE;
+    g_return_val_if_fail(tested_name && is_display_name(tested_name), FALSE);
+
+    cached_name += NAME_PREFIX_LENGTH;
+    cached_name_end = strchr(cached_name, ':');
+    if (cached_name_end)
+        cached_name_length = cached_name_end - cached_name;
     else
-        return TRUE;
+        cached_name_length = strlen(cached_name);
 
-    if (*display_name == '\0')
-        return TRUE;
-    if (strcmp(display_name, get_default_display_name()) == 0)
-        return TRUE;
-    return FALSE;
+    tested_name += NAME_PREFIX_LENGTH;
+    tested_name_end = strchr(tested_name, ':');
+    if (tested_name_end)
+        tested_name_length = tested_name_end - tested_name;
+    else
+        tested_name_length = strlen(tested_name);
+
+    if (cached_name_length != tested_name_length)
+        return FALSE;
+    if (strncmp(cached_name, tested_name, cached_name_length) != 0)
+        return FALSE;
+
+    /* XXX: handle screen number? */
+    return TRUE;
 }
 
 static void
@@ -88,6 +107,29 @@ gst_vaapi_display_x11_finalize(GObject *object)
     G_OBJECT_CLASS(gst_vaapi_display_x11_parent_class)->finalize(object);
 }
 
+/* Reconstruct a display name without our prefix */
+static const gchar *
+get_display_name(gpointer ptr)
+{
+    GstVaapiDisplayX11 * const display = GST_VAAPI_DISPLAY_X11(ptr);
+    const gchar *display_name = display->priv->display_name;
+
+    if (!display_name)
+        return NULL;
+
+    if (is_display_name(display_name)) {
+        display_name += NAME_PREFIX_LENGTH;
+        if (*display_name == '\0')
+            return NULL;
+        return display_name;
+    }
+
+    /* XXX: this should not happen */
+    g_assert(0 && "display name without prefix");
+    return display_name;
+}
+
+/* Mangle display name with our prefix */
 static void
 set_display_name(GstVaapiDisplayX11 *display, const gchar *display_name)
 {
@@ -95,10 +137,12 @@ set_display_name(GstVaapiDisplayX11 *display, const gchar *display_name)
 
     g_free(priv->display_name);
 
-    if (display_name)
-        priv->display_name = g_strdup(display_name);
-    else
-        priv->display_name = NULL;
+    if (!display_name) {
+        display_name = get_default_display_name();
+        if (!display_name)
+            display_name = "";
+    }
+    priv->display_name = g_strdup_printf("%s%s", NAME_PREFIX, display_name);
 }
 
 static void
@@ -157,7 +201,7 @@ gst_vaapi_display_x11_get_property(
         g_value_set_boolean(value, display->priv->synchronous);
         break;
     case PROP_DISPLAY_NAME:
-        g_value_set_string(value, display->priv->display_name);
+        g_value_set_string(value, get_display_name(display));
         break;
     case PROP_X11_DISPLAY:
         g_value_set_pointer(value, gst_vaapi_display_x11_get_display(display));
@@ -211,7 +255,7 @@ gst_vaapi_display_x11_open_display(GstVaapiDisplay *display)
         GST_VAAPI_DISPLAY_X11(display)->priv;
 
     if (priv->create_display) {
-        priv->x11_display = XOpenDisplay(priv->display_name);
+        priv->x11_display = XOpenDisplay(get_display_name(display));
         if (!priv->x11_display)
             return FALSE;
         priv->x11_screen = DefaultScreen(priv->x11_display);
@@ -283,7 +327,8 @@ gst_vaapi_display_x11_get_display_info(
     cache = gst_vaapi_display_get_cache();
     if (!cache)
         return FALSE;
-    cached_info = gst_vaapi_display_cache_lookup_by_native_display(cache, priv->x11_display);
+    cached_info = gst_vaapi_display_cache_lookup_by_native_display(
+        cache, priv->x11_display);
     if (cached_info) {
         *info = *cached_info;
         return TRUE;