vulkan: move fullscreenquad object to library
authorMatthew Waters <matthew@centricular.com>
Fri, 29 Nov 2019 02:45:42 +0000 (13:45 +1100)
committerMatthew Waters <matthew@centricular.com>
Wed, 4 Dec 2019 07:20:27 +0000 (07:20 +0000)
It's useful and extensible enough to be used by us and other elements

19 files changed:
ext/vulkan/meson.build
ext/vulkan/vkcolorconvert.c
ext/vulkan/vkcolorconvert.h
ext/vulkan/vkelementutils.c [deleted file]
ext/vulkan/vkelementutils.h [deleted file]
ext/vulkan/vkimageidentity.c
ext/vulkan/vkimageidentity.h
ext/vulkan/vkshader.c [deleted file]
ext/vulkan/vkshader.h [deleted file]
ext/vulkan/vkviewconvert.c
ext/vulkan/vkviewconvert.h
gst-libs/gst/vulkan/gstvkfullscreenquad.c [moved from ext/vulkan/vkfullscreenquad.c with 91% similarity]
gst-libs/gst/vulkan/gstvkfullscreenquad.h [moved from ext/vulkan/vkfullscreenquad.h with 89% similarity]
gst-libs/gst/vulkan/gstvkutils.c
gst-libs/gst/vulkan/gstvkutils.h
gst-libs/gst/vulkan/meson.build
gst-libs/gst/vulkan/vulkan.h
gst-libs/gst/vulkan/vulkan_fwd.h
tests/check/libs/vkimage.c

index 682da6d..03e50d0 100644 (file)
@@ -22,11 +22,8 @@ vulkan_sources = [
   'vkcolorconvert.c',
   'vkdownload.c',
   'vkdeviceprovider.c',
-  'vkelementutils.c',
-  'vkfullscreenquad.c',
   'vkimageidentity.c',
   'vksink.c',
-  'vkshader.c',
   'vkupload.c',
   'vkviewconvert.c',
 ]
index 9e14a8a..2c17f3b 100644 (file)
@@ -32,8 +32,6 @@
 #include <string.h>
 
 #include "vkcolorconvert.h"
-#include "vkshader.h"
-#include "vkelementutils.h"
 
 #include "shaders/identity.vert.h"
 #include "shaders/swizzle.frag.h"
@@ -1154,13 +1152,14 @@ gst_vulkan_color_convert_set_caps (GstBaseTransform * bt, GstCaps * in_caps,
   }
 
   if (!(vert =
-          _vk_create_shader (vfilter->device, identity_vert, identity_vert_size,
-              NULL))) {
+          gst_vulkan_create_shader (vfilter->device, identity_vert,
+              identity_vert_size, NULL))) {
     return FALSE;
   }
   if (!(frag =
-          _vk_create_shader (vfilter->device, conv->current_shader->frag_code,
-              conv->current_shader->frag_size, NULL))) {
+          gst_vulkan_create_shader (vfilter->device,
+              conv->current_shader->frag_code, conv->current_shader->frag_size,
+              NULL))) {
     gst_vulkan_handle_unref (vert);
     return FALSE;
   }
@@ -1224,7 +1223,7 @@ gst_vulkan_color_convert_transform (GstBaseTransform * bt, GstBuffer * inbuf,
       goto error;
     }
     in_img_views[i] =
-        get_or_create_image_view ((GstVulkanImageMemory *) img_mem);
+        gst_vulkan_get_or_create_image_view ((GstVulkanImageMemory *) img_mem);
     gst_vulkan_trash_list_add (conv->quad->trash_list,
         gst_vulkan_trash_list_acquire (conv->quad->trash_list, fence,
             gst_vulkan_trash_mini_object_unref,
@@ -1296,7 +1295,8 @@ gst_vulkan_color_convert_transform (GstBaseTransform * bt, GstBuffer * inbuf,
         goto error;
       }
       render_img_views[i] =
-          get_or_create_image_view ((GstVulkanImageMemory *) img_mem);
+          gst_vulkan_get_or_create_image_view ((GstVulkanImageMemory *)
+          img_mem);
       gst_vulkan_trash_list_add (conv->quad->trash_list,
           gst_vulkan_trash_list_acquire (conv->quad->trash_list, fence,
               gst_vulkan_trash_mini_object_unref,
index f27734b..8c14381 100644 (file)
@@ -24,7 +24,6 @@
 #include <gst/gst.h>
 #include <gst/video/video.h>
 #include <gst/vulkan/vulkan.h>
-#include "vkfullscreenquad.h"
 
 G_BEGIN_DECLS
 
diff --git a/ext/vulkan/vkelementutils.c b/ext/vulkan/vkelementutils.c
deleted file mode 100644 (file)
index 82f50b5..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * GStreamer
- * Copyright (C) 2019 Matthew Waters <matthew@centricular.com>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#ifdef HAVE_CONFIG_H
-#include "config.h"
-#endif
-
-#include "vkelementutils.h"
-
-static void
-fill_vulkan_image_view_info (VkImage image, VkFormat format,
-    VkImageViewCreateInfo * info)
-{
-  /* *INDENT-OFF* */
-  *info = (VkImageViewCreateInfo) {
-      .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
-      .pNext = NULL,
-      .image = image,
-      .format = format,
-      .viewType = VK_IMAGE_VIEW_TYPE_2D,
-      .flags = 0,
-      .components = (VkComponentMapping) {
-          VK_COMPONENT_SWIZZLE_R,
-          VK_COMPONENT_SWIZZLE_G,
-          VK_COMPONENT_SWIZZLE_B,
-          VK_COMPONENT_SWIZZLE_A
-      },
-      .subresourceRange = (VkImageSubresourceRange) {
-          .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
-          .baseMipLevel = 0,
-          .levelCount = 1,
-          .baseArrayLayer = 0,
-          .layerCount = 1,
-      }
-  };
-  /* *INDENT-ON* */
-}
-
-static gboolean
-find_compatible_view (GstVulkanImageView * view, VkImageViewCreateInfo * info)
-{
-  return view->create_info.image == info->image
-      && view->create_info.format == info->format
-      && view->create_info.viewType == info->viewType
-      && view->create_info.flags == info->flags
-      && view->create_info.components.r == info->components.r
-      && view->create_info.components.g == info->components.g
-      && view->create_info.components.b == info->components.b
-      && view->create_info.components.a == info->components.a
-      && view->create_info.subresourceRange.aspectMask ==
-      info->subresourceRange.aspectMask
-      && view->create_info.subresourceRange.baseMipLevel ==
-      info->subresourceRange.baseMipLevel
-      && view->create_info.subresourceRange.levelCount ==
-      info->subresourceRange.levelCount
-      && view->create_info.subresourceRange.levelCount ==
-      info->subresourceRange.levelCount
-      && view->create_info.subresourceRange.baseArrayLayer ==
-      info->subresourceRange.baseArrayLayer
-      && view->create_info.subresourceRange.layerCount ==
-      info->subresourceRange.layerCount;
-}
-
-GstVulkanImageView *
-get_or_create_image_view (GstVulkanImageMemory * image)
-{
-  VkImageViewCreateInfo create_info;
-  GstVulkanImageView *ret = NULL;
-
-  fill_vulkan_image_view_info (image->image, image->create_info.format,
-      &create_info);
-
-  ret = gst_vulkan_image_memory_find_view (image,
-      (GstVulkanImageMemoryFindViewFunc) find_compatible_view, &create_info);
-  if (!ret) {
-    ret = gst_vulkan_image_view_new (image, &create_info);
-    gst_vulkan_image_memory_add_view (image, ret);
-  }
-
-  return ret;
-}
diff --git a/ext/vulkan/vkelementutils.h b/ext/vulkan/vkelementutils.h
deleted file mode 100644 (file)
index 1fdc4ea..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * GStreamer
- * Copyright (C) 2019 Matthew Waters <matthew@centricular.com>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#ifndef _VK_ELEMENT_UTILS_H_
-#define _VK_ELEMENT_UTILS_H_
-
-#include <gst/gst.h>
-#include <gst/vulkan/vulkan.h>
-
-G_BEGIN_DECLS
-
-GstVulkanImageView *        get_or_create_image_view            (GstVulkanImageMemory * image);
-
-G_END_DECLS
-
-#endif
index e1c471f..d897217 100644 (file)
@@ -32,8 +32,6 @@
 #include <string.h>
 
 #include "vkimageidentity.h"
-#include "vkshader.h"
-#include "vkelementutils.h"
 
 #include "shaders/identity.vert.h"
 #include "shaders/identity.frag.h"
@@ -148,10 +146,10 @@ gst_vulkan_image_identity_start (GstBaseTransform * bt)
 
   vk_identity->quad = gst_vulkan_full_screen_quad_new (vfilter->queue);
 
-  if (!(vert = _vk_create_shader (vfilter->device, identity_vert,
+  if (!(vert = gst_vulkan_create_shader (vfilter->device, identity_vert,
               identity_vert_size, &error)))
     goto error;
-  if (!(frag = _vk_create_shader (vfilter->device, identity_frag,
+  if (!(frag = gst_vulkan_create_shader (vfilter->device, identity_frag,
               identity_frag_size, &error))) {
     gst_vulkan_handle_unref (vert);
     goto error;
index c24e5d8..f10994e 100644 (file)
@@ -24,7 +24,6 @@
 #include <gst/gst.h>
 #include <gst/video/video.h>
 #include <gst/vulkan/vulkan.h>
-#include "vkfullscreenquad.h"
 
 G_BEGIN_DECLS
 
diff --git a/ext/vulkan/vkshader.c b/ext/vulkan/vkshader.c
deleted file mode 100644 (file)
index 54a7862..0000000
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * GStreamer
- * Copyright (C) 2019 Matthew Waters <matthew@centricular.com>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#ifdef HAVE_CONFIG_H
-#include "config.h"
-#endif
-
-#include "vkshader.h"
-
-#define SPIRV_MAGIC_NUMBER_NE 0x07230203
-#define SPIRV_MAGIC_NUMBER_OE 0x03022307
-
-GstVulkanHandle *
-_vk_create_shader (GstVulkanDevice * device, gchar * code, gsize size,
-    GError ** error)
-{
-  VkShaderModule shader;
-  VkResult res;
-
-  /* *INDENT-OFF* */
-  VkShaderModuleCreateInfo info = {
-      .sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO,
-      .pNext = NULL,
-      .flags = 0,
-      .codeSize = size,
-      .pCode = (guint32 *) code
-  };
-  /* *INDENT-ON* */
-  guint32 first_word;
-  guint32 *new_code = NULL;
-
-  g_return_val_if_fail (size >= 4, VK_NULL_HANDLE);
-  g_return_val_if_fail (size % 4 == 0, VK_NULL_HANDLE);
-
-  first_word = code[0] | code[1] << 8 | code[2] << 16 | code[3] << 24;
-  g_return_val_if_fail (first_word == SPIRV_MAGIC_NUMBER_NE
-      || first_word == SPIRV_MAGIC_NUMBER_OE, VK_NULL_HANDLE);
-  if (first_word == SPIRV_MAGIC_NUMBER_OE) {
-    /* endianness swap... */
-    guint32 *old_code = (guint32 *) code;
-    gsize i;
-
-    GST_DEBUG ("performaing endianness conversion on spirv shader of size %"
-        G_GSIZE_FORMAT, size);
-    new_code = g_new0 (guint32, size / 4);
-
-    for (i = 0; i < size / 4; i++) {
-      guint32 old = old_code[i];
-      guint32 new = 0;
-
-      new |= (old & 0xff) << 24;
-      new |= (old & 0xff00) << 8;
-      new |= (old & 0xff0000) >> 8;
-      new |= (old & 0xff000000) >> 24;
-      new_code[i] = new;
-    }
-
-    first_word = ((guint32 *) new_code)[0];
-    g_assert (first_word == SPIRV_MAGIC_NUMBER_NE);
-
-    info.pCode = new_code;
-  }
-
-  res = vkCreateShaderModule (device->device, &info, NULL, &shader);
-  g_free (new_code);
-  if (gst_vulkan_error_to_g_error (res, error, "VkCreateShaderModule") < 0)
-    return NULL;
-
-  return gst_vulkan_handle_new_wrapped (device, GST_VULKAN_HANDLE_TYPE_SHADER,
-      (GstVulkanHandleTypedef) shader, gst_vulkan_handle_free_shader, NULL);
-}
diff --git a/ext/vulkan/vkshader.h b/ext/vulkan/vkshader.h
deleted file mode 100644 (file)
index b819c48..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * GStreamer
- * Copyright (C) 2019 Matthew Waters <matthew@centricular.com>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#ifndef _VK_SHADER_H_
-#define _VK_SHADER_H_
-
-#include <gst/gst.h>
-#include <gst/vulkan/vulkan.h>
-
-G_BEGIN_DECLS
-
-GstVulkanHandle * _vk_create_shader (GstVulkanDevice * device, gchar * code, gsize size, GError ** error);
-
-#endif
index c37b6d2..dae6bb5 100644 (file)
@@ -32,8 +32,6 @@
 #include <string.h>
 
 #include "vkviewconvert.h"
-#include "vkshader.h"
-#include "vkelementutils.h"
 
 #include "shaders/identity.vert.h"
 #include "shaders/view_convert.frag.h"
@@ -1842,12 +1840,12 @@ gst_vulkan_view_convert_start (GstBaseTransform * bt)
   conv->quad = gst_vulkan_full_screen_quad_new (vfilter->queue);
 
   if (!(vert =
-          _vk_create_shader (vfilter->device, identity_vert, identity_vert_size,
-              NULL))) {
+          gst_vulkan_create_shader (vfilter->device, identity_vert,
+              identity_vert_size, NULL))) {
     return FALSE;
   }
   if (!(frag =
-          _vk_create_shader (vfilter->device, view_convert_frag,
+          gst_vulkan_create_shader (vfilter->device, view_convert_frag,
               view_convert_frag_size, NULL))) {
     gst_vulkan_handle_unref (vert);
     return FALSE;
@@ -1927,7 +1925,7 @@ gst_vulkan_view_convert_transform (GstBaseTransform * bt, GstBuffer * inbuf,
       goto error;
     }
     in_img_views[i] =
-        get_or_create_image_view ((GstVulkanImageMemory *) img_mem);
+        gst_vulkan_get_or_create_image_view ((GstVulkanImageMemory *) img_mem);
     gst_vulkan_trash_list_add (conv->quad->trash_list,
         gst_vulkan_trash_list_acquire (conv->quad->trash_list, fence,
             gst_vulkan_trash_mini_object_unref,
@@ -1940,7 +1938,8 @@ gst_vulkan_view_convert_transform (GstBaseTransform * bt, GstBuffer * inbuf,
           "Output memory must be a GstVulkanImageMemory");
       goto error;
     }
-    out_img_views[i] = get_or_create_image_view ((GstVulkanImageMemory *) mem);
+    out_img_views[i] =
+        gst_vulkan_get_or_create_image_view ((GstVulkanImageMemory *) mem);
     gst_vulkan_trash_list_add (conv->quad->trash_list,
         gst_vulkan_trash_list_acquire (conv->quad->trash_list, fence,
             gst_vulkan_trash_mini_object_unref,
index f05f5ac..809301c 100644 (file)
@@ -24,7 +24,6 @@
 #include <gst/gst.h>
 #include <gst/video/video.h>
 #include <gst/vulkan/vulkan.h>
-#include "vkfullscreenquad.h"
 
 G_BEGIN_DECLS
 
similarity index 91%
rename from ext/vulkan/vkfullscreenquad.c
rename to gst-libs/gst/vulkan/gstvkfullscreenquad.c
index 4f35c61..369d264 100644 (file)
 #include "config.h"
 #endif
 
-#include "vkfullscreenquad.h"
-#include "vkelementutils.h"
+#include "gstvkfullscreenquad.h"
 
 #define GST_CAT_DEFAULT gst_vulkan_full_screen_quad_debug
 GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT);
 
-typedef struct _GstVulkanFullScreenQuad GstVulkanFullScreenQuad;
+/* XXX: privatise this on moving to lib */
+struct Vertex
+{
+  float x, y, z;
+  float s, t;
+};
 
 struct _GstVulkanFullScreenQuadPrivate
 {
@@ -41,9 +45,6 @@ struct _GstVulkanFullScreenQuadPrivate
   GstMemory *uniforms;
   gsize uniform_size;
 
-  GstMemory *push_constants;
-  gsize push_constants_size;
-
   GstVulkanHandle *vert;
   GstVulkanHandle *frag;
 };
@@ -739,7 +740,42 @@ clear_uniform_data (GstVulkanFullScreenQuad * self)
 }
 
 static void
-destroy_pipeline (GstVulkanFullScreenQuad * self)
+clear_index_data (GstVulkanFullScreenQuad * self)
+{
+  GstVulkanFullScreenQuadPrivate *priv = GET_PRIV (self);
+  GstVulkanFence *last_fence =
+      LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
+
+  if (priv->indices)
+    gst_vulkan_trash_list_add (self->trash_list,
+        gst_vulkan_trash_list_acquire (self->trash_list, last_fence,
+            gst_vulkan_trash_mini_object_unref,
+            (GstMiniObject *) priv->indices));
+  priv->indices = NULL;
+  priv->n_indices = 0;
+
+  gst_vulkan_fence_unref (last_fence);
+}
+
+static void
+clear_vertex_data (GstVulkanFullScreenQuad * self)
+{
+  GstVulkanFullScreenQuadPrivate *priv = GET_PRIV (self);
+  GstVulkanFence *last_fence =
+      LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
+
+  if (priv->vertices)
+    gst_vulkan_trash_list_add (self->trash_list,
+        gst_vulkan_trash_list_acquire (self->trash_list, last_fence,
+            gst_vulkan_trash_mini_object_unref,
+            (GstMiniObject *) priv->vertices));
+  priv->vertices = NULL;
+
+  gst_vulkan_fence_unref (last_fence);
+}
+
+static void
+clear_render_pass (GstVulkanFullScreenQuad * self)
 {
   GstVulkanFence *last_fence =
       LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
@@ -750,18 +786,48 @@ destroy_pipeline (GstVulkanFullScreenQuad * self)
             gst_vulkan_trash_mini_object_unref,
             (GstMiniObject *) self->render_pass));
   self->render_pass = NULL;
+
+  gst_vulkan_fence_unref (last_fence);
+}
+
+static void
+clear_pipeline_layout (GstVulkanFullScreenQuad * self)
+{
+  GstVulkanFence *last_fence =
+      LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
+
   if (self->pipeline_layout)
     gst_vulkan_trash_list_add (self->trash_list,
         gst_vulkan_trash_list_acquire (self->trash_list, last_fence,
             gst_vulkan_trash_mini_object_unref,
             (GstMiniObject *) self->pipeline_layout));
   self->pipeline_layout = NULL;
+
+  gst_vulkan_fence_unref (last_fence);
+}
+
+static void
+clear_graphics_pipeline (GstVulkanFullScreenQuad * self)
+{
+  GstVulkanFence *last_fence =
+      LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
+
   if (self->graphics_pipeline)
     gst_vulkan_trash_list_add (self->trash_list,
         gst_vulkan_trash_list_acquire (self->trash_list, last_fence,
             gst_vulkan_trash_mini_object_unref,
             (GstMiniObject *) self->graphics_pipeline));
   self->graphics_pipeline = NULL;
+
+  gst_vulkan_fence_unref (last_fence);
+}
+
+static void
+clear_descriptor_set_layout (GstVulkanFullScreenQuad * self)
+{
+  GstVulkanFence *last_fence =
+      LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
+
   if (self->descriptor_set_layout)
     gst_vulkan_trash_list_add (self->trash_list,
         gst_vulkan_trash_list_acquire (self->trash_list, last_fence,
@@ -770,6 +836,20 @@ destroy_pipeline (GstVulkanFullScreenQuad * self)
   self->descriptor_set_layout = NULL;
 
   gst_vulkan_fence_unref (last_fence);
+}
+
+static void
+destroy_pipeline (GstVulkanFullScreenQuad * self)
+{
+  GstVulkanFence *last_fence =
+      LAST_FENCE_OR_ALWAYS_SIGNALLED (self, self->queue->device);
+
+  clear_render_pass (self);
+  clear_pipeline_layout (self);
+  clear_graphics_pipeline (self);
+  clear_descriptor_set_layout (self);
+
+  gst_vulkan_fence_unref (last_fence);
 
   gst_vulkan_trash_list_gc (self->trash_list);
 }
@@ -807,14 +887,13 @@ gst_vulkan_full_screen_quad_finalize (GObject * object)
   clear_descriptor_cache (self);
   clear_shaders (self);
   clear_uniform_data (self);
+  clear_index_data (self);
+  clear_vertex_data (self);
 
   gst_vulkan_trash_list_wait (self->trash_list, -1);
   gst_vulkan_trash_list_gc (self->trash_list);
   gst_clear_object (&self->trash_list);
 
-  gst_clear_mini_object (((GstMiniObject **) & priv->vertices));
-  gst_clear_mini_object (((GstMiniObject **) & priv->indices));
-
   gst_clear_mini_object (((GstMiniObject **) & self->last_fence));
 
   gst_clear_object (&self->queue);
@@ -923,6 +1002,47 @@ gst_vulkan_full_screen_quad_set_uniform_buffer (GstVulkanFullScreenQuad * self,
   return TRUE;
 }
 
+gboolean
+gst_vulkan_full_screen_quad_set_index_buffer (GstVulkanFullScreenQuad * self,
+    GstMemory * indices, gsize n_indices, GError ** error)
+{
+  GstVulkanFullScreenQuadPrivate *priv;
+
+  g_return_val_if_fail (GST_IS_VULKAN_FULL_SCREEN_QUAD (self), FALSE);
+  g_return_val_if_fail (indices == NULL
+      || gst_is_vulkan_buffer_memory (indices), FALSE);
+
+  priv = GET_PRIV (self);
+
+  clear_index_data (self);
+  if (indices) {
+    priv->indices = gst_memory_ref (indices);
+    priv->n_indices = n_indices;
+  }
+
+  return TRUE;
+}
+
+gboolean
+gst_vulkan_full_screen_quad_set_vertex_buffer (GstVulkanFullScreenQuad * self,
+    GstMemory * vertices, GError ** error)
+{
+  GstVulkanFullScreenQuadPrivate *priv;
+
+  g_return_val_if_fail (GST_IS_VULKAN_FULL_SCREEN_QUAD (self), FALSE);
+  g_return_val_if_fail (vertices == NULL
+      || gst_is_vulkan_buffer_memory (vertices), FALSE);
+
+  priv = GET_PRIV (self);
+
+  clear_vertex_data (self);
+  if (vertices) {
+    priv->vertices = gst_memory_ref (vertices);
+  }
+
+  return TRUE;
+}
+
 static GstVulkanImageMemory *
 peek_image_from_buffer (GstBuffer * buffer, guint i)
 {
@@ -942,34 +1062,34 @@ ensure_vertex_data (GstVulkanFullScreenQuad * self, GError ** error)
         sizeof (vertices), VK_BUFFER_USAGE_VERTEX_BUFFER_BIT,
         VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT |
         VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
-  }
 
-  if (!gst_memory_map (priv->vertices, &map_info, GST_MAP_WRITE)) {
-    g_set_error_literal (error, GST_VULKAN_ERROR, VK_ERROR_MEMORY_MAP_FAILED,
-        "Failed to map memory");
-    goto failure;
-  }
+    if (!gst_memory_map (priv->vertices, &map_info, GST_MAP_WRITE)) {
+      g_set_error_literal (error, GST_VULKAN_ERROR, VK_ERROR_MEMORY_MAP_FAILED,
+          "Failed to map memory");
+      goto failure;
+    }
 
-  memcpy (map_info.data, vertices, map_info.size);
-  gst_memory_unmap (priv->vertices, &map_info);
+    memcpy (map_info.data, vertices, map_info.size);
+    gst_memory_unmap (priv->vertices, &map_info);
+  }
 
   if (!priv->indices) {
     priv->indices = gst_vulkan_buffer_memory_alloc (self->queue->device,
         sizeof (indices), VK_BUFFER_USAGE_INDEX_BUFFER_BIT,
         VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT |
         VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
-  }
 
-  if (!gst_memory_map (priv->indices, &map_info, GST_MAP_WRITE)) {
-    g_set_error_literal (error, GST_VULKAN_ERROR, VK_ERROR_MEMORY_MAP_FAILED,
-        "Failed to map memory");
-    goto failure;
-  }
+    if (!gst_memory_map (priv->indices, &map_info, GST_MAP_WRITE)) {
+      g_set_error_literal (error, GST_VULKAN_ERROR, VK_ERROR_MEMORY_MAP_FAILED,
+          "Failed to map memory");
+      goto failure;
+    }
 
-  memcpy (map_info.data, indices, map_info.size);
-  gst_memory_unmap (priv->indices, &map_info);
+    memcpy (map_info.data, indices, map_info.size);
+    gst_memory_unmap (priv->indices, &map_info);
 
-  priv->n_indices = G_N_ELEMENTS (indices);
+    priv->n_indices = G_N_ELEMENTS (indices);
+  }
 
   return TRUE;
 
@@ -1080,7 +1200,7 @@ gst_vulkan_full_screen_quad_prepare_draw (GstVulkanFullScreenQuad * self,
             "Input memory must be a GstVulkanImageMemory");
         goto error;
       }
-      in_views[i] = get_or_create_image_view (img_mem);
+      in_views[i] = gst_vulkan_get_or_create_image_view (img_mem);
       gst_vulkan_trash_list_add (self->trash_list,
           gst_vulkan_trash_list_acquire (self->trash_list, fence,
               gst_vulkan_trash_mini_object_unref,
@@ -1099,7 +1219,7 @@ gst_vulkan_full_screen_quad_prepare_draw (GstVulkanFullScreenQuad * self,
             "Output memory must be a GstVulkanImageMemory");
         goto error;
       }
-      out_views[i] = get_or_create_image_view (img_mem);
+      out_views[i] = gst_vulkan_get_or_create_image_view (img_mem);
       gst_vulkan_trash_list_add (self->trash_list,
           gst_vulkan_trash_list_acquire (self->trash_list, fence,
               gst_vulkan_trash_mini_object_unref,
@@ -1154,7 +1274,7 @@ gst_vulkan_full_screen_quad_fill_command_buffer (GstVulkanFullScreenQuad * self,
           "Input memory must be a GstVulkanImageMemory");
       goto error;
     }
-    in_views[i] = get_or_create_image_view (img_mem);
+    in_views[i] = gst_vulkan_get_or_create_image_view (img_mem);
     gst_vulkan_trash_list_add (self->trash_list,
         gst_vulkan_trash_list_acquire (self->trash_list, fence,
             gst_vulkan_trash_mini_object_unref, (GstMiniObject *) in_views[i]));
@@ -1166,7 +1286,7 @@ gst_vulkan_full_screen_quad_fill_command_buffer (GstVulkanFullScreenQuad * self,
           "Output memory must be a GstVulkanImageMemory");
       goto error;
     }
-    out_views[i] = get_or_create_image_view (img_mem);
+    out_views[i] = gst_vulkan_get_or_create_image_view (img_mem);
     gst_vulkan_trash_list_add (self->trash_list,
         gst_vulkan_trash_list_acquire (self->trash_list, fence,
             gst_vulkan_trash_mini_object_unref,
similarity index 89%
rename from ext/vulkan/vkfullscreenquad.h
rename to gst-libs/gst/vulkan/gstvkfullscreenquad.h
index f73748c..8cdb218 100644 (file)
@@ -28,6 +28,7 @@
 
 G_BEGIN_DECLS
 
+GST_VULKAN_API
 GType gst_vulkan_full_screen_quad_get_type (void);
 #define GST_TYPE_VULKAN_FULL_SCREEN_QUAD            (gst_vulkan_full_screen_quad_get_type ())
 #define GST_VULKAN_FULL_SCREEN_QUAD(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), GST_TYPE_VULKAN_FULL_SCREEN_QUAD, GstVulkanFullScreenQuad))
@@ -36,17 +37,6 @@ GType gst_vulkan_full_screen_quad_get_type (void);
 #define GST_IS_VULKAN_FULL_SCREEN_QUAD_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GST_TYPE_VULKAN_FULL_SCREEN_QUAD))
 #define GST_VULKAN_FULL_SCREEN_QUAD_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), GST_TYPE_VULKAN_FULL_SCREEN_QUAD, GstVulkanFullScreenQuadClass))
 
-/* XXX: privatise this on moving to lib */
-struct Vertex
-{
-  float x, y, z;
-  float s, t;
-};
-
-typedef struct _GstVulkanFullScreenQuad GstVulkanFullScreenQuad;
-typedef struct _GstVulkanFullScreenQuadClass GstVulkanFullScreenQuadClass;
-typedef struct _GstVulkanFullScreenQuadPrivate GstVulkanFullScreenQuadPrivate;
-
 struct _GstVulkanFullScreenQuad
 {
   GstObject                         parent;
@@ -76,20 +66,35 @@ struct _GstVulkanFullScreenQuadClass
   GstObjectClass                    parent_class;
 };
 
+GST_VULKAN_API
 GstVulkanFullScreenQuad *   gst_vulkan_full_screen_quad_new         (GstVulkanQueue * queue);
 
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_set_info            (GstVulkanFullScreenQuad * self, GstVideoInfo *in_info, GstVideoInfo * out_info);
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_set_shaders         (GstVulkanFullScreenQuad * self, GstVulkanHandle * vert, GstVulkanHandle * frag);
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_set_uniform_buffer  (GstVulkanFullScreenQuad * self, GstMemory * uniforms, GError ** error);
+GST_VULKAN_API
+gboolean            gst_vulkan_full_screen_quad_set_vertex_buffer   (GstVulkanFullScreenQuad * self, GstMemory * vertices, GError ** error);
+GST_VULKAN_API
+gboolean            gst_vulkan_full_screen_quad_set_index_buffer    (GstVulkanFullScreenQuad * self, GstMemory * indices, gsize n_indices, GError ** error);
 
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_set_input_buffer    (GstVulkanFullScreenQuad * self, GstBuffer * buffer, GError ** error);
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_set_output_buffer   (GstVulkanFullScreenQuad * self, GstBuffer * buffer, GError ** error);
 
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_prepare_draw        (GstVulkanFullScreenQuad * self, GstVulkanFence * fence, GError ** error);
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_fill_command_buffer (GstVulkanFullScreenQuad * self, GstVulkanCommandBuffer * cmd, GstVulkanFence * fence, GError ** error);
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_submit              (GstVulkanFullScreenQuad * self, GstVulkanCommandBuffer * cmd, GstVulkanFence * fence, GError ** error);
+GST_VULKAN_API
 gboolean            gst_vulkan_full_screen_quad_draw                (GstVulkanFullScreenQuad * self, GError ** error);
 
+GST_VULKAN_API
 GstVulkanFence *    gst_vulkan_full_screen_quad_get_last_fence      (GstVulkanFullScreenQuad * self);
 
 G_END_DECLS
index b75417e..812e251 100644 (file)
@@ -402,3 +402,139 @@ gst_vulkan_handle_context_query (GstElement * element, GstQuery * query,
 
   return FALSE;
 }
+
+static void
+fill_vulkan_image_view_info (VkImage image, VkFormat format,
+    VkImageViewCreateInfo * info)
+{
+  /* *INDENT-OFF* */
+  *info = (VkImageViewCreateInfo) {
+      .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
+      .pNext = NULL,
+      .image = image,
+      .format = format,
+      .viewType = VK_IMAGE_VIEW_TYPE_2D,
+      .flags = 0,
+      .components = (VkComponentMapping) {
+          VK_COMPONENT_SWIZZLE_R,
+          VK_COMPONENT_SWIZZLE_G,
+          VK_COMPONENT_SWIZZLE_B,
+          VK_COMPONENT_SWIZZLE_A
+      },
+      .subresourceRange = (VkImageSubresourceRange) {
+          .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
+          .baseMipLevel = 0,
+          .levelCount = 1,
+          .baseArrayLayer = 0,
+          .layerCount = 1,
+      }
+  };
+  /* *INDENT-ON* */
+}
+
+static gboolean
+find_compatible_view (GstVulkanImageView * view, VkImageViewCreateInfo * info)
+{
+  return view->create_info.image == info->image
+      && view->create_info.format == info->format
+      && view->create_info.viewType == info->viewType
+      && view->create_info.flags == info->flags
+      && view->create_info.components.r == info->components.r
+      && view->create_info.components.g == info->components.g
+      && view->create_info.components.b == info->components.b
+      && view->create_info.components.a == info->components.a
+      && view->create_info.subresourceRange.aspectMask ==
+      info->subresourceRange.aspectMask
+      && view->create_info.subresourceRange.baseMipLevel ==
+      info->subresourceRange.baseMipLevel
+      && view->create_info.subresourceRange.levelCount ==
+      info->subresourceRange.levelCount
+      && view->create_info.subresourceRange.levelCount ==
+      info->subresourceRange.levelCount
+      && view->create_info.subresourceRange.baseArrayLayer ==
+      info->subresourceRange.baseArrayLayer
+      && view->create_info.subresourceRange.layerCount ==
+      info->subresourceRange.layerCount;
+}
+
+GstVulkanImageView *
+gst_vulkan_get_or_create_image_view (GstVulkanImageMemory * image)
+{
+  VkImageViewCreateInfo create_info;
+  GstVulkanImageView *ret = NULL;
+
+  fill_vulkan_image_view_info (image->image, image->create_info.format,
+      &create_info);
+
+  ret = gst_vulkan_image_memory_find_view (image,
+      (GstVulkanImageMemoryFindViewFunc) find_compatible_view, &create_info);
+  if (!ret) {
+    ret = gst_vulkan_image_view_new (image, &create_info);
+    gst_vulkan_image_memory_add_view (image, ret);
+  }
+
+  return ret;
+}
+
+#define SPIRV_MAGIC_NUMBER_NE 0x07230203
+#define SPIRV_MAGIC_NUMBER_OE 0x03022307
+
+GstVulkanHandle *
+gst_vulkan_create_shader (GstVulkanDevice * device, gchar * code, gsize size,
+    GError ** error)
+{
+  VkShaderModule shader;
+  VkResult res;
+
+  /* *INDENT-OFF* */
+  VkShaderModuleCreateInfo info = {
+      .sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO,
+      .pNext = NULL,
+      .flags = 0,
+      .codeSize = size,
+      .pCode = (guint32 *) code
+  };
+  /* *INDENT-ON* */
+  guint32 first_word;
+  guint32 *new_code = NULL;
+
+  g_return_val_if_fail (size >= 4, VK_NULL_HANDLE);
+  g_return_val_if_fail (size % 4 == 0, VK_NULL_HANDLE);
+
+  first_word = code[0] | code[1] << 8 | code[2] << 16 | code[3] << 24;
+  g_return_val_if_fail (first_word == SPIRV_MAGIC_NUMBER_NE
+      || first_word == SPIRV_MAGIC_NUMBER_OE, VK_NULL_HANDLE);
+  if (first_word == SPIRV_MAGIC_NUMBER_OE) {
+    /* endianness swap... */
+    guint32 *old_code = (guint32 *) code;
+    gsize i;
+
+    GST_DEBUG ("performaing endianness conversion on spirv shader of size %"
+        G_GSIZE_FORMAT, size);
+    new_code = g_new0 (guint32, size / 4);
+
+    for (i = 0; i < size / 4; i++) {
+      guint32 old = old_code[i];
+      guint32 new = 0;
+
+      new |= (old & 0xff) << 24;
+      new |= (old & 0xff00) << 8;
+      new |= (old & 0xff0000) >> 8;
+      new |= (old & 0xff000000) >> 24;
+      new_code[i] = new;
+    }
+
+    first_word = ((guint32 *) new_code)[0];
+    g_assert (first_word == SPIRV_MAGIC_NUMBER_NE);
+
+    info.pCode = new_code;
+  }
+
+  res = vkCreateShaderModule (device->device, &info, NULL, &shader);
+  g_free (new_code);
+  if (gst_vulkan_error_to_g_error (res, error, "VkCreateShaderModule") < 0)
+    return NULL;
+
+  return gst_vulkan_handle_new_wrapped (device, GST_VULKAN_HANDLE_TYPE_SHADER,
+      (GstVulkanHandleTypedef) shader, gst_vulkan_handle_free_shader, NULL);
+}
index fc9231c..194650e 100644 (file)
@@ -52,6 +52,15 @@ gboolean                gst_vulkan_run_query                    (GstElement * el
                                                                  GstQuery * query,
                                                                  GstPadDirection direction);
 
+GST_VULKAN_API
+GstVulkanImageView *    gst_vulkan_get_or_create_image_view     (GstVulkanImageMemory * image);
+
+GST_VULKAN_API
+GstVulkanHandle *       gst_vulkan_create_shader                (GstVulkanDevice * device,
+                                                                 gchar * code,
+                                                                 gsize size,
+                                                                 GError ** error);
+
 G_END_DECLS
 
 #endif /*_VK_UTILS_H_ */
index 8b3268e..31cac19 100644 (file)
@@ -17,6 +17,7 @@ vulkan_sources = [
   'gstvkerror.c',
   'gstvkfence.c',
   'gstvkformat.c',
+  'gstvkfullscreenquad.c',
   'gstvkhandle.c',
   'gstvkhandlepool.c',
   'gstvkimagememory.c',
@@ -49,6 +50,7 @@ vulkan_headers = [
   'gstvkerror.h',
   'gstvkfence.h',
   'gstvkformat.h',
+  'gstvkfullscreenquad.h',
   'gstvkhandle.h',
   'gstvkhandlepool.h',
   'gstvkimagememory.h',
index bdf10f4..07e44ab 100644 (file)
 #include <gst/gst.h>
 
 #include <gst/vulkan/gstvkapi.h>
-
-/* helper vulkan objects */
 #include <gst/vulkan/gstvkdebug.h>
 #include <gst/vulkan/gstvkerror.h>
+#include <gst/vulkan/gstvkformat.h>
+
+/* vulkan wrapper objects */
 #include <gst/vulkan/gstvkinstance.h>
 #include <gst/vulkan/gstvkphysicaldevice.h>
 #include <gst/vulkan/gstvkdevice.h>
 #include <gst/vulkan/gstvkqueue.h>
 #include <gst/vulkan/gstvkfence.h>
-#include <gst/vulkan/gstvkformat.h>
 #include <gst/vulkan/gstvkdisplay.h>
 #include <gst/vulkan/gstvkwindow.h>
 #include <gst/vulkan/gstvkmemory.h>
 #include <gst/vulkan/gstvkimageview.h>
 #include <gst/vulkan/gstvkbufferpool.h>
 #include <gst/vulkan/gstvkimagebufferpool.h>
-#include <gst/vulkan/gstvkutils.h>
 #include <gst/vulkan/gstvkcommandbuffer.h>
 #include <gst/vulkan/gstvkcommandpool.h>
-#include <gst/vulkan/gstvkdescriptorcache.h>
 #include <gst/vulkan/gstvkdescriptorset.h>
 #include <gst/vulkan/gstvkdescriptorpool.h>
 #include <gst/vulkan/gstvkhandle.h>
-#include <gst/vulkan/gstvkhandlepool.h>
-#include <gst/vulkan/gstvktrash.h>
-#include <gst/vulkan/gstvkswapper.h>
 
 /* helper elements */
 #include <gst/vulkan/gstvkvideofilter.h>
 
+/* helper vulkan objects */
+#include <gst/vulkan/gstvkdescriptorcache.h>
+#include <gst/vulkan/gstvktrash.h>
+#include <gst/vulkan/gstvkswapper.h>
+#include <gst/vulkan/gstvkhandlepool.h>
+#include <gst/vulkan/gstvkfullscreenquad.h>
+
+#include <gst/vulkan/gstvkutils.h>
+
 #endif /* __GST_VULKAN_H__ */
index f489fc3..8634b28 100644 (file)
@@ -108,6 +108,10 @@ typedef struct _GstVulkanTrashListClass GstVulkanTrashListClass;
 
 typedef struct _GstVulkanTrash GstVulkanTrash;
 
+typedef struct _GstVulkanFullScreenQuad GstVulkanFullScreenQuad;
+typedef struct _GstVulkanFullScreenQuadClass GstVulkanFullScreenQuadClass;
+typedef struct _GstVulkanFullScreenQuadPrivate GstVulkanFullScreenQuadPrivate;
+
 G_END_DECLS
 
 #endif /* __GST_VULKAN_FWD_H__ */
index ffa13f4..09999b7 100644 (file)
@@ -26,8 +26,6 @@
 #include <gst/check/gstcheck.h>
 #include <gst/check/gstharness.h>
 #include <gst/vulkan/vulkan.h>
-#include "../../ext/vulkan/vkelementutils.h"
-#include "../../ext/vulkan/vkelementutils.c"
 
 static GstVulkanInstance *instance;
 static GstVulkanDevice *device;
@@ -115,7 +113,7 @@ GST_START_TEST (test_image_view_new)
   gst_video_info_set_format (&v_info, GST_VIDEO_FORMAT_RGBA, 16, 16);
   vk_mem = create_image_mem (&v_info);
 
-  view = get_or_create_image_view (vk_mem);
+  view = gst_vulkan_get_or_create_image_view (vk_mem);
 
   gst_vulkan_image_view_unref (view);
   gst_memory_unref ((GstMemory *) vk_mem);
@@ -132,9 +130,9 @@ GST_START_TEST (test_image_view_get)
   gst_video_info_set_format (&v_info, GST_VIDEO_FORMAT_RGBA, 16, 16);
   vk_mem = create_image_mem (&v_info);
 
-  view = get_or_create_image_view (vk_mem);
+  view = gst_vulkan_get_or_create_image_view (vk_mem);
   gst_vulkan_image_view_unref (view);
-  view = get_or_create_image_view (vk_mem);
+  view = gst_vulkan_get_or_create_image_view (vk_mem);
   gst_vulkan_image_view_unref (view);
 
   gst_memory_unref ((GstMemory *) vk_mem);
@@ -173,7 +171,7 @@ get_unref_image_view (GstHarnessThread * thread, struct view_stress *stress)
   GstVulkanImageView *view;
 
   mem = g_queue_peek_nth (stress->memories, rand);
-  view = get_or_create_image_view (mem);
+  view = gst_vulkan_get_or_create_image_view (mem);
   gst_vulkan_image_view_unref (view);
 
   g_atomic_int_inc (&stress->n_ops);