/*
 * GStreamer
 * Copyright (C) 2012-2014 Matthew Waters <ystree00@gmail.com>
 * Copyright (C) 2017 Sebastian Dröge <sebastian@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 <stdio.h>
#include <string.h>

#include "gl.h"
#include "gstglupload.h"

#if GST_GL_HAVE_PLATFORM_EGL
#include "egl/gsteglimage.h"
#include "egl/gstglmemoryegl.h"
#include "egl/gstglcontext_egl.h"
#endif

#if GST_GL_HAVE_DMABUF
#include <gst/allocators/gstdmabuf.h>
#endif

#if GST_GL_HAVE_VIV_DIRECTVIV
#include <gst/allocators/gstphysmemory.h>
#include <gst/gl/gstglfuncs.h>
#endif

#if GST_GL_HAVE_IONDMA
#include <gst/allocators/gstionmemory.h>
#endif

#if GST_GL_HAVE_PHYMEM
#include "gstglphymemory.h"
#endif

/**
 * SECTION:gstglupload
 * @title: GstGLUpload
 * @short_description: an object that uploads to GL textures
 * @see_also: #GstGLDownload, #GstGLMemory
 *
 * #GstGLUpload is an object that uploads data from system memory into GL textures.
 *
 * A #GstGLUpload can be created with gst_gl_upload_new()
 */

#define USING_OPENGL(context) (gst_gl_context_check_gl_version (context, GST_GL_API_OPENGL, 1, 0))
#define USING_OPENGL3(context) (gst_gl_context_check_gl_version (context, GST_GL_API_OPENGL3, 3, 1))
#define USING_GLES(context) (gst_gl_context_check_gl_version (context, GST_GL_API_GLES, 1, 0))
#define USING_GLES2(context) (gst_gl_context_check_gl_version (context, GST_GL_API_GLES2, 2, 0))
#define USING_GLES3(context) (gst_gl_context_check_gl_version (context, GST_GL_API_GLES2, 3, 0))

#define DEFAULT_ALIGN 16

GST_DEBUG_CATEGORY_STATIC (gst_gl_upload_debug);
#define GST_CAT_DEFAULT gst_gl_upload_debug

#define DEBUG_INIT \
  GST_DEBUG_CATEGORY_INIT (gst_gl_upload_debug, "glupload", 0, "upload");

G_DEFINE_TYPE_WITH_CODE (GstGLUpload, gst_gl_upload, GST_TYPE_OBJECT,
    DEBUG_INIT);
static void gst_gl_upload_finalize (GObject * object);

#define GST_GL_UPLOAD_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE ((obj), \
    GST_TYPE_GL_UPLOAD, GstGLUploadPrivate))

static GstGLTextureTarget
_caps_get_texture_target (GstCaps * caps, GstGLTextureTarget default_target)
{
  GstGLTextureTarget ret = 0;
  GstStructure *s = gst_caps_get_structure (caps, 0);

  if (gst_structure_has_field_typed (s, "texture-target", G_TYPE_STRING)) {
    const gchar *target_str = gst_structure_get_string (s, "texture-target");
    ret = gst_gl_texture_target_from_string (target_str);
  }

  if (!ret)
    ret = default_target;

  return ret;
}

/* Define the maximum number of planes we can upload - handle 2 views per buffer */
#define GST_GL_UPLOAD_MAX_PLANES (GST_VIDEO_MAX_PLANES * 2)

typedef struct _UploadMethod UploadMethod;

struct _GstGLUploadPrivate
{
  GstVideoInfo in_info;
  GstVideoInfo out_info;
  GstCaps *in_caps;
  GstCaps *out_caps;

  GstBuffer *outbuf;

  /* all method impl pointers */
  gpointer *upload_impl;

  /* current method */
  const UploadMethod *method;
  gpointer method_impl;
  int method_i;
};

static GstCaps *
_set_caps_features_with_passthrough (const GstCaps * caps,
    const gchar * feature_name, GstCapsFeatures * passthrough)
{
  guint i, j, m, n;
  GstCaps *tmp;

  tmp = gst_caps_new_empty ();

  n = gst_caps_get_size (caps);
  for (i = 0; i < n; i++) {
    GstCapsFeatures *features, *orig_features;
    GstStructure *s = gst_caps_get_structure (caps, i);

    orig_features = gst_caps_get_features (caps, i);
    features = gst_caps_features_new (feature_name, NULL);

    if (gst_caps_features_is_any (orig_features)) {
      /* if we have any features, we add both the features with and without @passthrough */
      gst_caps_append_structure_full (tmp, gst_structure_copy (s),
          gst_caps_features_copy (features));

      m = gst_caps_features_get_size (passthrough);
      for (j = 0; j < m; j++) {
        const gchar *feature = gst_caps_features_get_nth (passthrough, j);

        /* if we already have the features */
        if (gst_caps_features_contains (features, feature))
          continue;

        gst_caps_features_add (features, feature);
      }
    } else {
      m = gst_caps_features_get_size (orig_features);
      for (j = 0; j < m; j++) {
        const gchar *feature = gst_caps_features_get_nth (orig_features, j);

        /* if we already have the features */
        if (gst_caps_features_contains (features, feature))
          continue;

        if (g_strcmp0 (feature, GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY) == 0)
          continue;

        if (gst_caps_features_contains (passthrough, feature)) {
          gst_caps_features_add (features, feature);
        }
      }
    }

    gst_caps_append_structure_full (tmp, gst_structure_copy (s), features);
  }

  return tmp;
}

static GstCaps *
_caps_intersect_texture_target (GstCaps * caps, GstGLTextureTarget target_mask)
{
  GValue targets = G_VALUE_INIT;
  GstCaps *ret, *target;

  target = gst_caps_copy (caps);
  gst_gl_value_set_texture_target_from_mask (&targets, target_mask);
  gst_caps_set_value (target, "texture-target", &targets);

  ret = gst_caps_intersect_full (caps, target, GST_CAPS_INTERSECT_FIRST);

  g_value_unset (&targets);
  gst_caps_unref (target);
  return ret;
}

typedef enum
{
  METHOD_FLAG_CAN_SHARE_CONTEXT = 1,
} GstGLUploadMethodFlags;

struct _UploadMethod
{
  const gchar *name;
  GstGLUploadMethodFlags flags;

  GstStaticCaps *input_template_caps;

    gpointer (*new) (GstGLUpload * upload);
  GstCaps *(*transform_caps) (gpointer impl, GstGLContext * context,
      GstPadDirection direction, GstCaps * caps);
    gboolean (*accept) (gpointer impl, GstBuffer * buffer, GstCaps * in_caps,
      GstCaps * out_caps);
  void (*propose_allocation) (gpointer impl, GstQuery * decide_query,
      GstQuery * query);
    GstGLUploadReturn (*perform) (gpointer impl, GstBuffer * buffer,
      GstBuffer ** outbuf);
  void (*free) (gpointer impl);
} _UploadMethod;

struct GLMemoryUpload
{
  GstGLUpload *upload;
  GstGLTextureTarget input_target;
  GstGLTextureTarget output_target;
};

static gpointer
_gl_memory_upload_new (GstGLUpload * upload)
{
  struct GLMemoryUpload *mem = g_new0 (struct GLMemoryUpload, 1);

  mem->upload = upload;
  mem->input_target = GST_GL_TEXTURE_TARGET_NONE;
  mem->output_target = GST_GL_TEXTURE_TARGET_NONE;

  return mem;
}

static GstCaps *
_gl_memory_upload_transform_caps (gpointer impl, GstGLContext * context,
    GstPadDirection direction, GstCaps * caps)
{
  struct GLMemoryUpload *upload = impl;
  GstCapsFeatures *passthrough =
      gst_caps_features_from_string
      (GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION);
  GstCaps *ret;

  ret =
      _set_caps_features_with_passthrough (caps,
      GST_CAPS_FEATURE_MEMORY_GL_MEMORY, passthrough);

  gst_caps_features_free (passthrough);

  if (direction == GST_PAD_SINK) {
    GstCaps *tmp;
    GstGLTextureTarget target_mask;

    if (upload->input_target != GST_GL_TEXTURE_TARGET_NONE) {
      target_mask = 1 << upload->input_target;
    } else {
      target_mask = 1 << GST_GL_TEXTURE_TARGET_2D |
          1 << GST_GL_TEXTURE_TARGET_RECTANGLE |
          1 << GST_GL_TEXTURE_TARGET_EXTERNAL_OES;
    }

    tmp = _caps_intersect_texture_target (ret, target_mask);
    gst_caps_unref (ret);
    ret = tmp;
  } else {
    gint i, n;

    n = gst_caps_get_size (ret);
    for (i = 0; i < n; i++) {
      GstStructure *s = gst_caps_get_structure (ret, i);

      gst_structure_remove_fields (s, "texture-target", NULL);
    }
  }

  return ret;
}

static gboolean
_gl_memory_upload_accept (gpointer impl, GstBuffer * buffer, GstCaps * in_caps,
    GstCaps * out_caps)
{
  struct GLMemoryUpload *upload = impl;
  GstCapsFeatures *features;
  int i;

  features = gst_caps_get_features (out_caps, 0);
  if (!gst_caps_features_contains (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY))
    return FALSE;

  features = gst_caps_get_features (in_caps, 0);
  if (!gst_caps_features_contains (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY)
      && !gst_caps_features_contains (features,
          GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY))
    return FALSE;

  if (buffer) {
    GstVideoInfo *in_info = &upload->upload->priv->in_info;
    guint expected_memories = GST_VIDEO_INFO_N_PLANES (in_info);

    /* Support stereo views for separated multiview mode */
    if (GST_VIDEO_INFO_MULTIVIEW_MODE (in_info) ==
        GST_VIDEO_MULTIVIEW_MODE_SEPARATED)
      expected_memories *= GST_VIDEO_INFO_VIEWS (in_info);

    if (gst_buffer_n_memory (buffer) != expected_memories)
      return FALSE;

    for (i = 0; i < expected_memories; i++) {
      GstMemory *mem = gst_buffer_peek_memory (buffer, i);

      if (!gst_is_gl_memory (mem))
        return FALSE;
    }
  }

  return TRUE;
}

static void
_gl_memory_upload_propose_allocation (gpointer impl, GstQuery * decide_query,
    GstQuery * query)
{
  struct GLMemoryUpload *upload = impl;
  GstBufferPool *pool = NULL;
  guint n_pools, i;
  GstCaps *caps;
  GstCapsFeatures *features;

  gst_query_parse_allocation (query, &caps, NULL);
  if (caps == NULL)
    goto invalid_caps;
  features = gst_caps_get_features (caps, 0);

  /* Only offer our custom allocator if that type of memory was negotiated. */
  if (gst_caps_features_contains (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY)) {
    GstAllocator *allocator;
    GstAllocationParams params;
    gst_allocation_params_init (&params);

    allocator =
        GST_ALLOCATOR (gst_gl_memory_allocator_get_default (upload->
            upload->context));
    gst_query_add_allocation_param (query, allocator, &params);
    gst_object_unref (allocator);

#if GST_GL_HAVE_PLATFORM_EGL
    if (upload->upload->context
        && gst_gl_context_get_gl_platform (upload->upload->context) ==
        GST_GL_PLATFORM_EGL) {
      allocator =
          GST_ALLOCATOR (gst_allocator_find (GST_GL_MEMORY_EGL_ALLOCATOR_NAME));
      gst_query_add_allocation_param (query, allocator, &params);
      gst_object_unref (allocator);
    }
#endif
  }

  n_pools = gst_query_get_n_allocation_pools (query);
  for (i = 0; i < n_pools; i++) {
    gst_query_parse_nth_allocation_pool (query, i, &pool, NULL, NULL, NULL);
    if (!GST_IS_GL_BUFFER_POOL (pool)) {
      gst_object_unref (pool);
      pool = NULL;
    }
  }

  if (!pool) {
    GstStructure *config;
    GstVideoInfo info;
    gsize size;


    if (!gst_video_info_from_caps (&info, caps))
      goto invalid_caps;

    pool = gst_gl_buffer_pool_new (upload->upload->context);
    config = gst_buffer_pool_get_config (pool);

    /* the normal size of a frame */
    size = info.size;
    gst_buffer_pool_config_set_params (config, caps, size, 0, 0);
    gst_buffer_pool_config_add_option (config,
        GST_BUFFER_POOL_OPTION_GL_SYNC_META);
    if (upload->upload->priv->out_caps) {
      GstGLTextureTarget target;
      const gchar *target_pool_option_str;

      target =
          _caps_get_texture_target (upload->upload->priv->out_caps,
          GST_GL_TEXTURE_TARGET_2D);
      target_pool_option_str =
          gst_gl_texture_target_to_buffer_pool_option (target);
      gst_buffer_pool_config_add_option (config, target_pool_option_str);
    }

    if (!gst_buffer_pool_set_config (pool, config)) {
      gst_object_unref (pool);
      goto config_failed;
    }

    gst_query_add_allocation_pool (query, pool, size, 1, 0);
  }

  if (pool)
    gst_object_unref (pool);

  return;

invalid_caps:
  {
    GST_WARNING_OBJECT (upload->upload, "invalid caps specified");
    return;
  }
config_failed:
  {
    GST_WARNING_OBJECT (upload->upload, "failed setting config");
    return;
  }
}

static GstGLUploadReturn
_gl_memory_upload_perform (gpointer impl, GstBuffer * buffer,
    GstBuffer ** outbuf)
{
  struct GLMemoryUpload *upload = impl;
  GstGLMemory *gl_mem;
  int i, n;

  n = gst_buffer_n_memory (buffer);
  for (i = 0; i < n; i++) {
    GstMemory *mem = gst_buffer_peek_memory (buffer, i);

    gl_mem = (GstGLMemory *) mem;
    if (!gst_gl_context_can_share (upload->upload->context,
            gl_mem->mem.context))
      return GST_GL_UPLOAD_UNSHARED_GL_CONTEXT;

    if (upload->output_target == GST_GL_TEXTURE_TARGET_NONE &&
        upload->upload->priv->out_caps) {
      upload->output_target =
          _caps_get_texture_target (upload->upload->priv->out_caps,
          GST_GL_TEXTURE_TARGET_NONE);
    }

    /* always track the last input texture target so ::transform_caps() can
     * use it to build the output caps */
    upload->input_target = gl_mem->tex_target;
    if (upload->output_target != gl_mem->tex_target) {
      *outbuf = NULL;
      return GST_GL_UPLOAD_RECONFIGURE;
    }

    if (gst_is_gl_memory_pbo (mem))
      gst_gl_memory_pbo_upload_transfer ((GstGLMemoryPBO *) mem);
  }

  *outbuf = gst_buffer_ref (buffer);

  return GST_GL_UPLOAD_DONE;
}

static void
_gl_memory_upload_free (gpointer impl)
{
  g_free (impl);
}


static GstStaticCaps _gl_memory_upload_caps =
GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE_WITH_FEATURES
    (GST_CAPS_FEATURE_MEMORY_GL_MEMORY, GST_GL_MEMORY_VIDEO_FORMATS_STR));

static const UploadMethod _gl_memory_upload = {
  "GLMemory",
  METHOD_FLAG_CAN_SHARE_CONTEXT,
  &_gl_memory_upload_caps,
  &_gl_memory_upload_new,
  &_gl_memory_upload_transform_caps,
  &_gl_memory_upload_accept,
  &_gl_memory_upload_propose_allocation,
  &_gl_memory_upload_perform,
  &_gl_memory_upload_free
};

#if GST_GL_HAVE_DMABUF
struct DmabufUpload
{
  GstGLUpload *upload;

  GstEGLImage *eglimage[GST_VIDEO_MAX_PLANES];
  GstBuffer *inbuf;
  GstBuffer *outbuf;
  GstBufferPool *pool;
  GstGLVideoAllocationParams *params;
};

static GstStaticCaps _dma_buf_upload_caps =
    GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE_WITH_FEATURES
    (GST_CAPS_FEATURE_MEMORY_DMABUF,
        GST_GL_MEMORY_VIDEO_FORMATS_STR) ";"
    GST_VIDEO_CAPS_MAKE (GST_GL_MEMORY_VIDEO_FORMATS_STR));

static gpointer
_dma_buf_upload_new (GstGLUpload * upload)
{
  struct DmabufUpload *dmabuf = g_new0 (struct DmabufUpload, 1);
  dmabuf->upload = upload;
  return dmabuf;
}

static GstCaps *
_dma_buf_upload_transform_caps (gpointer impl, GstGLContext * context,
    GstPadDirection direction, GstCaps * caps)
{
  struct DmabufUpload *dmabuf = impl;
  GstCapsFeatures *passthrough =
      gst_caps_features_from_string
      (GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION);
  GstCaps *ret;

  if (direction == GST_PAD_SINK) {
    gint i, n;
    GstCaps *tmp;

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_GL_MEMORY, passthrough);

    gst_caps_set_simple (ret, "format", G_TYPE_STRING, "RGBA", NULL);

    n = gst_caps_get_size (ret);
    for (i = 0; i < n; i++) {
      GstStructure *s = gst_caps_get_structure (ret, i);
      gst_structure_remove_fields (s, "chroma-site", NULL);
      gst_structure_remove_fields (s, "colorimetry", NULL);
    }
    tmp = _caps_intersect_texture_target (ret, 1 << GST_GL_TEXTURE_TARGET_2D);
    gst_caps_unref (ret);
    ret = tmp;
  } else {
    gint i, n;
    GstCaps *tmp;
    GValue formats = G_VALUE_INIT;
    gchar *format_str = g_strdup (GST_GL_MEMORY_VIDEO_FORMATS_STR);

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_DMABUF, passthrough);
    tmp =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY, passthrough);
    gst_caps_append (ret, tmp);

    g_value_init (&formats, GST_TYPE_LIST);
    gst_value_deserialize (&formats, format_str);
    tmp = gst_caps_copy (ret);
    gst_caps_set_value (tmp, "format", &formats);
    gst_caps_append (ret, tmp);
    g_free (format_str);
    g_value_unset (&formats);

    n = gst_caps_get_size (ret);
    for (i = 0; i < n; i++) {
      GstStructure *s = gst_caps_get_structure (ret, i);

      gst_structure_remove_fields (s, "texture-target", NULL);
    }
  }

  gst_caps_features_free (passthrough);

  GST_DEBUG_OBJECT (dmabuf->upload, "transformed %" GST_PTR_FORMAT " into %"
      GST_PTR_FORMAT, caps, ret);

  return ret;
}

/* This qdata based caching isn't thread safe and thus prohibits the use
 * of tees and queues upstream from glupload. The result can be a
 * double free of EGLImage with ensuing memory corruption.
 * It was added as a bandaid for some cache flush issue observed only
 * on Mali/Exynos. Upstream indicates that it's going away soon.
 *
 * https://gitlab.freedesktop.org/gstreamer/gst-plugins-base/issues/375
 * https://gitlab.freedesktop.org/gstreamer/gst-plugins-base/issues/659
 */

#if 1
static void
_dma_buf_upload_unref_eglimages (struct DmabufUpload *dmabuf)
{
  gint i;

  for (i = 0; i < G_N_ELEMENTS (dmabuf->eglimage); i++) {
    if (dmabuf->eglimage[i]) {
      gst_egl_image_unref (dmabuf->eglimage[i]);
      dmabuf->eglimage[i] = NULL;
    }
  }
}

static GstEGLImage *
_get_cached_eglimage (GstMemory * mem, gint plane)
{
  return NULL;
}

static void
_set_cached_eglimage (GstMemory * mem, GstEGLImage * eglimage, gint plane)
{
}
#else
static void
_dma_buf_upload_unref_eglimages (struct DmabufUpload *dmabuf)
{
}

static GQuark
_eglimage_quark (gint plane)
{
  static GQuark quark[4] = { 0 };
  static const gchar *quark_str[] = {
    "GstGLDMABufEGLImage0",
    "GstGLDMABufEGLImage1",
    "GstGLDMABufEGLImage2",
    "GstGLDMABufEGLImage3",
  };

  if (!quark[plane])
    quark[plane] = g_quark_from_static_string (quark_str[plane]);

  return quark[plane];
}

static GstEGLImage *
_get_cached_eglimage (GstMemory * mem, gint plane)
{
  return gst_mini_object_get_qdata (GST_MINI_OBJECT (mem),
      _eglimage_quark (plane));
}

static void
_set_cached_eglimage (GstMemory * mem, GstEGLImage * eglimage, gint plane)
{
  return gst_mini_object_set_qdata (GST_MINI_OBJECT (mem),
      _eglimage_quark (plane), eglimage, (GDestroyNotify) gst_egl_image_unref);
}
#endif

static gboolean
_dma_buf_upload_setup_buffer_pool (GstBufferPool **pool, GstAllocator *allocator,
    GstCaps *caps, GstVideoInfo *info)
{
  GstAllocationParams params;
  GstStructure *config;
  gsize size;
  guint width, height;
  GstVideoAlignment alignment;
 
  g_return_val_if_fail (caps != NULL && info != NULL, FALSE);

  width = GST_VIDEO_INFO_WIDTH (info);
  height = GST_VIDEO_INFO_HEIGHT (info);

  gst_allocation_params_init (&params);

  /* if user not provide an allocator, then use default ion allocator*/
  if (!allocator) {
#if GST_GL_HAVE_IONDMA
    allocator = gst_ion_allocator_obtain ();
#endif
  }

  if (!allocator) {
    GST_WARNING ("Cannot get available allocator");
    return FALSE;
  }
  GST_DEBUG ("got allocator(%p).", allocator);

  if (*pool)
    gst_object_unref(*pool);

  *pool = gst_video_buffer_pool_new ();
  if (!*pool) {
    GST_WARNING ("New video buffer pool failed.");
    return FALSE;
  }
  GST_DEBUG ("create buffer pool(%p).", *pool);

  config = gst_buffer_pool_get_config (*pool);

  /* configure alignment for eglimage to import this dma-fd buffer */
  memset (&alignment, 0, sizeof (GstVideoAlignment));
  alignment.padding_right = GST_ROUND_UP_N(width, DEFAULT_ALIGN) - width;
  alignment.padding_bottom = GST_ROUND_UP_N(height, DEFAULT_ALIGN) - height;
  GST_DEBUG ("align buffer pool, w(%d) h(%d), padding_right (%d), padding_bottom (%d)",
      width, height, alignment.padding_right, alignment.padding_bottom);

  /* the normal size of a frame */
  size = info->size;
  gst_buffer_pool_config_set_params (config, caps, size, 0, 30);
  gst_buffer_pool_config_add_option (config, GST_BUFFER_POOL_OPTION_VIDEO_META);
  gst_buffer_pool_config_add_option (config, GST_BUFFER_POOL_OPTION_VIDEO_ALIGNMENT);
  gst_buffer_pool_config_set_video_alignment (config, &alignment);
  gst_buffer_pool_config_set_allocator (config, allocator, &params);

  if (!gst_buffer_pool_set_config (*pool, config)) {
    GST_WARNING ("buffer pool config failed.");
    gst_object_unref (*pool);
    return FALSE;
  }

  return TRUE;
}

static gboolean
_dma_buf_upload_accept (gpointer impl, GstBuffer * buffer, GstCaps * in_caps,
    GstCaps * out_caps)
{
  struct DmabufUpload *dmabuf = impl;
  GstVideoInfo *in_info = &dmabuf->upload->priv->in_info;
  guint n_planes = GST_VIDEO_INFO_N_PLANES (in_info);
  GstVideoMeta *meta;
  GstVideoCropMeta *crop;
  guint n_mem;
  guint mems_idx[GST_VIDEO_MAX_PLANES];
  gsize mems_skip[GST_VIDEO_MAX_PLANES];
  GstMemory *mems[GST_VIDEO_MAX_PLANES];
  guint i;
  GstVideoFormat out_fmt;

  n_mem = gst_buffer_n_memory (buffer);
  meta = gst_buffer_get_video_meta (buffer);
  crop = gst_buffer_get_video_crop_meta(buffer);

  /* dmabuf upload is only supported with EGL contexts. */
  if (gst_gl_context_get_gl_platform (dmabuf->upload->context) !=
      GST_GL_PLATFORM_EGL)
    return FALSE;

  if (!gst_gl_context_check_feature (dmabuf->upload->context,
          "EGL_KHR_image_base"))
    return FALSE;

  /* This will eliminate most non-dmabuf out there */
  if (!gst_is_dmabuf_memory (gst_buffer_peek_memory (buffer, 0))) {
    GstVideoFrame frame1, frame2;

    gst_video_frame_map (&frame1, in_info, buffer, GST_MAP_READ);

    if (!dmabuf->pool) {
      gboolean ret;
      GstCaps *new_caps = gst_video_info_to_caps(&frame1.info);
      gst_video_info_from_caps(in_info, new_caps);

      ret = _dma_buf_upload_setup_buffer_pool (&dmabuf->pool, NULL, new_caps, in_info);
      if (!ret) {
        gst_video_frame_unmap (&frame1);
        gst_caps_unref (new_caps);
        GST_WARNING_OBJECT (dmabuf->upload, "no available buffer pool");
        return FALSE;
      }
    }

    if (!gst_buffer_pool_is_active (dmabuf->pool)
        && gst_buffer_pool_set_active (dmabuf->pool, TRUE) != TRUE) {
      gst_video_frame_unmap (&frame1);
      GST_WARNING_OBJECT (dmabuf->upload, "buffer pool is not ok");
      return FALSE;
    }

    if (dmabuf->inbuf)
      gst_buffer_unref(dmabuf->inbuf);
    dmabuf->inbuf = NULL;

    gst_buffer_pool_acquire_buffer (dmabuf->pool, &dmabuf->inbuf, NULL);
    if (!dmabuf->inbuf) {
      gst_video_frame_unmap (&frame1);
      GST_WARNING_OBJECT (dmabuf->upload, "acquire_buffer failed");
      return FALSE;
    }

    GST_DEBUG_OBJECT (dmabuf->upload, "copy plane resolution (%d)x(%d)\n", in_info->width, in_info->height);
    gst_video_frame_map (&frame2, in_info, dmabuf->inbuf, GST_MAP_WRITE);
    gst_video_frame_copy (&frame2, &frame1);
    gst_video_frame_unmap (&frame1);
    gst_video_frame_unmap (&frame2);

    buffer = dmabuf->inbuf;
    meta = gst_buffer_get_video_meta (buffer);
  }

  /* We cannot have multiple dmabuf per plane */
  if (n_mem > n_planes)
    return FALSE;

  /* Update video info based on video meta */
  if (meta) {
    in_info->width = meta->width;
    in_info->height = meta->height;

    for (i = 0; i < meta->n_planes; i++) {
      in_info->offset[i] = meta->offset[i];
      in_info->stride[i] = meta->stride[i];
    }
  }

  if (crop) {
    in_info->width = MIN (crop->width, in_info->width);
    in_info->height = MIN (crop->height, in_info->height);

    GST_DEBUG_OBJECT (dmabuf->upload, "got crop meta (%d)x(%d)",
        in_info->width, in_info->height);
    gst_buffer_remove_meta (buffer, (GstMeta *)crop);
  }

  if (dmabuf->params)
    gst_gl_allocation_params_free ((GstGLAllocationParams *) dmabuf->params);
  if (!(dmabuf->params =
          gst_gl_video_allocation_params_new_wrapped_gl_handle (dmabuf->
              upload->context, NULL, &dmabuf->upload->priv->out_info, -1, NULL,
              GST_GL_TEXTURE_TARGET_2D, 0, NULL, NULL, NULL)))
    return FALSE;

  /* Find and validate all memories */
  for (i = 0; i < n_planes; i++) {
    guint plane_size;
    guint length;

    plane_size = gst_gl_get_plane_data_size (in_info, NULL, i);

    if (!gst_buffer_find_memory (buffer, in_info->offset[i], plane_size,
            &mems_idx[i], &length, &mems_skip[i]))
      return FALSE;

    /* We can't have more then one dmabuf per plane */
    if (length != 1)
      return FALSE;

    mems[i] = gst_buffer_peek_memory (buffer, mems_idx[i]);

    /* And all memory found must be dmabuf */
    if (!gst_is_dmabuf_memory (mems[i]))
      return FALSE;
  }

  _dma_buf_upload_unref_eglimages (dmabuf);

  out_fmt = GST_VIDEO_INFO_FORMAT (&dmabuf->upload->priv->out_info);
  if (out_fmt == GST_VIDEO_FORMAT_RGBA) {
    /* Now create one single EGLImage */
    /* check if one is cached */
    dmabuf->eglimage[0] = _get_cached_eglimage (mems[0], 0);
    if (dmabuf->eglimage[0])
      return TRUE;

    dmabuf->eglimage[0] =
        gst_egl_image_from_dmabuf_singleplaner (dmabuf->upload->context,
        mems, in_info, n_planes, mems_skip);
    if (!dmabuf->eglimage[0]) {
      _dma_buf_upload_unref_eglimages (dmabuf);
      return FALSE;
    }

    _set_cached_eglimage (mems[0], dmabuf->eglimage[0], 0);
  } else {
    /* Now create an EGLImage for each dmabufs */
    for (i = 0; i < n_planes; i++) {
      /* check if one is cached */
      dmabuf->eglimage[i] = _get_cached_eglimage (mems[i], i);
      if (dmabuf->eglimage[i])
        continue;

      /* otherwise create one and cache it */
      dmabuf->eglimage[i] =
          gst_egl_image_from_dmabuf (dmabuf->upload->context,
          gst_dmabuf_memory_get_fd (mems[i]), in_info, i,
          mems[i]->offset + mems_skip[i]);

      if (!dmabuf->eglimage[i]) {
        _dma_buf_upload_unref_eglimages (dmabuf);
        return FALSE;
      }

      _set_cached_eglimage (mems[i], dmabuf->eglimage[i], i);
    }
  }

  return TRUE;
}

static void
_dma_buf_upload_propose_allocation (gpointer impl, GstQuery * decide_query,
    GstQuery * query)
{
  /* nothing to do for now. */
  struct DmabufUpload *upload = impl;
  GstBufferPool *pool = NULL;
  GstAllocator *allocator = NULL;
  GstCaps *caps;
  GstVideoInfo info;

  gst_query_parse_allocation (query, &caps, NULL);

  if (!gst_video_info_from_caps (&info, caps))
    goto invalid_caps;

#if GST_GL_HAVE_IONDMA
  allocator = gst_ion_allocator_obtain ();
#endif
  if (!allocator) {
    GST_WARNING ("New ion allocator failed.");
    return;
  }
  GST_DEBUG ("create ion allocator(%p).", allocator);

  gst_query_add_allocation_param (query, allocator, NULL);

  if (!_dma_buf_upload_setup_buffer_pool (&pool, allocator, caps, &info))
    goto setup_failed;

  gst_query_set_nth_allocation_pool (query, 0, pool, info.size, 0, 30);

  if (pool)
    gst_object_unref (pool);

  return;
invalid_caps:
  {
    GST_WARNING_OBJECT (upload->upload, "invalid caps specified");
    return;
  }
setup_failed:
  {
    GST_WARNING_OBJECT (upload->upload, "failed to setup buffer pool");
    return;
  }
}

static void
_dma_buf_upload_perform_gl_thread (GstGLContext * context,
    struct DmabufUpload *dmabuf)
{
  GstGLMemoryAllocator *allocator;
  guint n_mem, i;

  allocator =
      GST_GL_MEMORY_ALLOCATOR (gst_allocator_find
      (GST_GL_MEMORY_EGL_ALLOCATOR_NAME));

  n_mem = GST_VIDEO_INFO_N_PLANES (dmabuf->params->v_info);
  for (i = 0; i < n_mem; i++) {
    if(!dmabuf->eglimage[i])
      return;
  }
  /* FIXME: buffer pool */
  dmabuf->outbuf = gst_buffer_new ();
  gst_gl_memory_setup_buffer (allocator, dmabuf->outbuf, dmabuf->params, NULL,
      (gpointer *) dmabuf->eglimage, gst_buffer_n_memory (dmabuf->outbuf));
  gst_object_unref (allocator);
}

static GstGLUploadReturn
_dma_buf_upload_perform (gpointer impl, GstBuffer * buffer, GstBuffer ** outbuf)
{
  struct DmabufUpload *dmabuf = impl;

  gst_gl_context_thread_add (dmabuf->upload->context,
      (GstGLContextThreadFunc) _dma_buf_upload_perform_gl_thread, dmabuf);

  _dma_buf_upload_unref_eglimages (dmabuf);

  if (!dmabuf->outbuf)
    return GST_GL_UPLOAD_ERROR;

  gst_buffer_add_parent_buffer_meta (dmabuf->outbuf, buffer);

  *outbuf = dmabuf->outbuf;
  dmabuf->outbuf = NULL;

  return GST_GL_UPLOAD_DONE;
}

static void
_dma_buf_upload_free (gpointer impl)
{
  struct DmabufUpload *dmabuf = impl;

  if (dmabuf->params)
    gst_gl_allocation_params_free ((GstGLAllocationParams *) dmabuf->params);

  if (dmabuf->inbuf)
    gst_buffer_unref (dmabuf->inbuf);

  if (dmabuf->pool)
    gst_object_unref(dmabuf->pool);

  _dma_buf_upload_unref_eglimages (dmabuf);

  g_free (impl);
}

static const UploadMethod _dma_buf_upload = {
  "Dmabuf",
  0,
  &_dma_buf_upload_caps,
  &_dma_buf_upload_new,
  &_dma_buf_upload_transform_caps,
  &_dma_buf_upload_accept,
  &_dma_buf_upload_propose_allocation,
  &_dma_buf_upload_perform,
  &_dma_buf_upload_free
};

#endif /* GST_GL_HAVE_DMABUF */

struct GLUploadMeta
{
  GstGLUpload *upload;

  gboolean result;
  GstVideoGLTextureUploadMeta *meta;
  guint texture_ids[GST_GL_UPLOAD_MAX_PLANES];
  GstBufferPool *pool;
};

static gpointer
_upload_meta_upload_new (GstGLUpload * upload)
{
  struct GLUploadMeta *meta = g_new0 (struct GLUploadMeta, 1);

  meta->upload = upload;
  meta->pool = NULL;

  return meta;
}

static GstCaps *
_upload_meta_upload_transform_caps (gpointer impl, GstGLContext * context,
    GstPadDirection direction, GstCaps * caps)
{
  GstCapsFeatures *passthrough =
      gst_caps_features_from_string
      (GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION);
  GstCaps *ret;

  if (direction == GST_PAD_SINK) {
    GstCaps *tmp;

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_GL_MEMORY, passthrough);

    tmp = _caps_intersect_texture_target (ret, 1 << GST_GL_TEXTURE_TARGET_2D);
    gst_caps_unref (ret);
    ret = tmp;
  } else {
    gint i, n;

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_META_GST_VIDEO_GL_TEXTURE_UPLOAD_META, passthrough);
    gst_caps_set_simple (ret, "format", G_TYPE_STRING, "RGBA", NULL);

    n = gst_caps_get_size (ret);
    for (i = 0; i < n; i++) {
      GstStructure *s = gst_caps_get_structure (ret, i);

      gst_structure_remove_fields (s, "texture-target", NULL);
    }
  }

  gst_caps_features_free (passthrough);

  return ret;
}

static gboolean
_upload_meta_upload_accept (gpointer impl, GstBuffer * buffer,
    GstCaps * in_caps, GstCaps * out_caps)
{
  struct GLUploadMeta *upload = impl;
  GstCapsFeatures *features;
  GstVideoGLTextureUploadMeta *meta;
  gboolean ret = TRUE;
  GstStructure *config;
  gsize size;

  features = gst_caps_get_features (in_caps, 0);

  if (!gst_caps_features_contains (features,
          GST_CAPS_FEATURE_META_GST_VIDEO_GL_TEXTURE_UPLOAD_META))
    ret = FALSE;

  features = gst_caps_get_features (out_caps, 0);
  if (!gst_caps_features_contains (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY))
    ret = FALSE;

  if (!ret)
    return ret;

  if (upload->pool == NULL)
    upload->pool = gst_gl_buffer_pool_new (upload->upload->context);

  if (!gst_buffer_pool_is_active (upload->pool)) {
    config = gst_buffer_pool_get_config (upload->pool);

    size = upload->upload->priv->in_info.size;
    gst_buffer_pool_config_set_params (config, in_caps, size, 0, 0);

    if (!gst_buffer_pool_set_config (upload->pool, config)) {
      GST_WARNING_OBJECT (upload->upload, "failed to set bufferpool config");
      return FALSE;
    }
    gst_buffer_pool_set_active (upload->pool, TRUE);
  }

  if (buffer) {
    if ((meta = gst_buffer_get_video_gl_texture_upload_meta (buffer)) == NULL)
      return FALSE;

    if (meta->texture_type[0] != GST_VIDEO_GL_TEXTURE_TYPE_RGBA) {
      GST_FIXME_OBJECT (upload, "only single rgba texture supported");
      return FALSE;
    }

    if (meta->texture_orientation !=
        GST_VIDEO_GL_TEXTURE_ORIENTATION_X_NORMAL_Y_NORMAL) {
      GST_FIXME_OBJECT (upload, "only x-normal, y-normal textures supported");
      return FALSE;
    }
  }

  return TRUE;
}

static void
_upload_meta_upload_propose_allocation (gpointer impl, GstQuery * decide_query,
    GstQuery * query)
{
  struct GLUploadMeta *upload = impl;
  GstStructure *gl_context;
  gchar *platform, *gl_apis;
  gpointer handle;

  gl_apis =
      gst_gl_api_to_string (gst_gl_context_get_gl_api (upload->upload->
          context));
  platform =
      gst_gl_platform_to_string (gst_gl_context_get_gl_platform (upload->
          upload->context));
  handle = (gpointer) gst_gl_context_get_gl_context (upload->upload->context);

  gl_context =
      gst_structure_new ("GstVideoGLTextureUploadMeta", "gst.gl.GstGLContext",
      GST_TYPE_GL_CONTEXT, upload->upload->context, "gst.gl.context.handle",
      G_TYPE_POINTER, handle, "gst.gl.context.type", G_TYPE_STRING, platform,
      "gst.gl.context.apis", G_TYPE_STRING, gl_apis, NULL);
  gst_query_add_allocation_meta (query,
      GST_VIDEO_GL_TEXTURE_UPLOAD_META_API_TYPE, gl_context);

  g_free (gl_apis);
  g_free (platform);
  gst_structure_free (gl_context);
}

/*
 * Uploads using gst_video_gl_texture_upload_meta_upload().
 * i.e. consumer of GstVideoGLTextureUploadMeta
 */
static void
_do_upload_with_meta (GstGLContext * context, struct GLUploadMeta *upload)
{
  if (!gst_video_gl_texture_upload_meta_upload (upload->meta,
          upload->texture_ids)) {
    upload->result = FALSE;
    return;
  }

  upload->result = TRUE;
}

static GstGLUploadReturn
_upload_meta_upload_perform (gpointer impl, GstBuffer * buffer,
    GstBuffer ** outbuf)
{
  struct GLUploadMeta *upload = impl;
  int i;
  GstVideoInfo *in_info = &upload->upload->priv->in_info;
  guint max_planes = GST_VIDEO_INFO_N_PLANES (in_info);

  /* Support stereo views for separated multiview mode */
  if (GST_VIDEO_INFO_MULTIVIEW_MODE (in_info) ==
      GST_VIDEO_MULTIVIEW_MODE_SEPARATED)
    max_planes *= GST_VIDEO_INFO_VIEWS (in_info);

  GST_LOG_OBJECT (upload, "Attempting upload with GstVideoGLTextureUploadMeta");

  upload->meta = gst_buffer_get_video_gl_texture_upload_meta (buffer);

  if (gst_buffer_pool_acquire_buffer (upload->pool, outbuf,
          NULL) != GST_FLOW_OK) {
    GST_WARNING_OBJECT (upload, "failed to acquire buffer from bufferpool");
    return GST_GL_UPLOAD_ERROR;
  }

  for (i = 0; i < GST_GL_UPLOAD_MAX_PLANES; i++) {
    guint tex_id = 0;

    if (i < max_planes) {
      GstMemory *mem = gst_buffer_peek_memory (*outbuf, i);
      tex_id = ((GstGLMemory *) mem)->tex_id;
    }

    upload->texture_ids[i] = tex_id;
  }

  GST_LOG ("Uploading with GLTextureUploadMeta with textures "
      "%i,%i,%i,%i / %i,%i,%i,%i",
      upload->texture_ids[0], upload->texture_ids[1],
      upload->texture_ids[2], upload->texture_ids[3],
      upload->texture_ids[4], upload->texture_ids[5],
      upload->texture_ids[6], upload->texture_ids[7]);

  gst_gl_context_thread_add (upload->upload->context,
      (GstGLContextThreadFunc) _do_upload_with_meta, upload);

  if (!upload->result)
    return GST_GL_UPLOAD_ERROR;

  return GST_GL_UPLOAD_DONE;
}

static void
_upload_meta_upload_free (gpointer impl)
{
  struct GLUploadMeta *upload = impl;

  g_return_if_fail (impl != NULL);

  if (upload->pool)
    gst_object_unref (upload->pool);

  g_free (upload);
}

static GstStaticCaps _upload_meta_upload_caps =
GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE_WITH_FEATURES
    (GST_CAPS_FEATURE_META_GST_VIDEO_GL_TEXTURE_UPLOAD_META, "RGBA"));

static const UploadMethod _upload_meta_upload = {
  "UploadMeta",
  METHOD_FLAG_CAN_SHARE_CONTEXT,
  &_upload_meta_upload_caps,
  &_upload_meta_upload_new,
  &_upload_meta_upload_transform_caps,
  &_upload_meta_upload_accept,
  &_upload_meta_upload_propose_allocation,
  &_upload_meta_upload_perform,
  &_upload_meta_upload_free
};

struct RawUploadFrame
{
  gint ref_count;
  GstVideoFrame frame;
};

struct RawUpload
{
  GstGLUpload *upload;
  struct RawUploadFrame *in_frame;
  GstGLVideoAllocationParams *params;
};

static struct RawUploadFrame *
_raw_upload_frame_new (struct RawUpload *raw, GstBuffer * buffer)
{
  struct RawUploadFrame *frame;
  GstVideoInfo *info;
  gint i;

  if (!buffer)
    return NULL;

  frame = g_slice_new (struct RawUploadFrame);
  frame->ref_count = 1;

  if (!gst_video_frame_map (&frame->frame, &raw->upload->priv->in_info,
          buffer, GST_MAP_READ)) {
    g_slice_free (struct RawUploadFrame, frame);
    return NULL;
  }

  raw->upload->priv->in_info = frame->frame.info;
  info = &raw->upload->priv->in_info;

  /* Recalculate the offsets (and size) */
  info->size = 0;
  for (i = 0; i < GST_VIDEO_INFO_N_PLANES (info); i++) {
    info->offset[i] = info->size;
    info->size += gst_gl_get_plane_data_size (info, NULL, i);
  }

  return frame;
}

static void
_raw_upload_frame_ref (struct RawUploadFrame *frame)
{
  g_atomic_int_inc (&frame->ref_count);
}

static void
_raw_upload_frame_unref (struct RawUploadFrame *frame)
{
  if (g_atomic_int_dec_and_test (&frame->ref_count)) {
    gst_video_frame_unmap (&frame->frame);
    g_slice_free (struct RawUploadFrame, frame);
  }
}

static gpointer
_raw_data_upload_new (GstGLUpload * upload)
{
  struct RawUpload *raw = g_new0 (struct RawUpload, 1);

  raw->upload = upload;

  return raw;
}

static GstCaps *
_raw_data_upload_transform_caps (gpointer impl, GstGLContext * context,
    GstPadDirection direction, GstCaps * caps)
{
  GstCapsFeatures *passthrough =
      gst_caps_features_from_string
      (GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION);
  GstCaps *ret;

  if (direction == GST_PAD_SINK) {
    GstGLTextureTarget target_mask = 0;
    GstCaps *tmp;

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_GL_MEMORY, passthrough);

    target_mask |= 1 << GST_GL_TEXTURE_TARGET_2D;
    target_mask |= 1 << GST_GL_TEXTURE_TARGET_RECTANGLE;
    tmp = _caps_intersect_texture_target (ret, target_mask);
    gst_caps_unref (ret);
    ret = tmp;
  } else {
    gint i, n;

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY, passthrough);

    n = gst_caps_get_size (ret);
    for (i = 0; i < n; i++) {
      GstStructure *s = gst_caps_get_structure (ret, i);

      gst_structure_remove_fields (s, "texture-target", NULL);
    }
  }

  gst_caps_features_free (passthrough);

  return ret;
}

static gboolean
_raw_data_upload_accept (gpointer impl, GstBuffer * buffer, GstCaps * in_caps,
    GstCaps * out_caps)
{
  struct RawUpload *raw = impl;
  GstCapsFeatures *features;

  features = gst_caps_get_features (out_caps, 0);
  if (!gst_caps_features_contains (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY))
    return FALSE;

  if (raw->in_frame)
    _raw_upload_frame_unref (raw->in_frame);
  raw->in_frame = _raw_upload_frame_new (raw, buffer);

  if (raw->params)
    gst_gl_allocation_params_free ((GstGLAllocationParams *) raw->params);
  if (!(raw->params =
          gst_gl_video_allocation_params_new_wrapped_data (raw->upload->context,
              NULL, &raw->upload->priv->in_info, -1, NULL,
              GST_GL_TEXTURE_TARGET_2D, 0, NULL, raw->in_frame,
              (GDestroyNotify) _raw_upload_frame_unref)))
    return FALSE;

  return (raw->in_frame != NULL);
}

static void
_raw_data_upload_propose_allocation (gpointer impl, GstQuery * decide_query,
    GstQuery * query)
{
  gst_query_add_allocation_meta (query, GST_VIDEO_META_API_TYPE, 0);
}

static GstGLUploadReturn
_raw_data_upload_perform (gpointer impl, GstBuffer * buffer,
    GstBuffer ** outbuf)
{
  GstGLBaseMemoryAllocator *allocator;
  struct RawUpload *raw = impl;
  int i;
  GstVideoInfo *in_info = &raw->upload->priv->in_info;
  guint n_mem = GST_VIDEO_INFO_N_PLANES (in_info);

  allocator =
      GST_GL_BASE_MEMORY_ALLOCATOR (gst_gl_memory_allocator_get_default
      (raw->upload->context));

  /* FIXME Use a buffer pool to cache the generated textures */
  /* FIXME: multiview support with separated left/right frames? */
  *outbuf = gst_buffer_new ();
  for (i = 0; i < n_mem; i++) {
    GstGLBaseMemory *tex;

    raw->params->parent.wrapped_data = raw->in_frame->frame.data[i];
    raw->params->plane = i;
    raw->params->tex_format =
        gst_gl_format_from_video_info (raw->upload->context, in_info, i);

    tex =
        gst_gl_base_memory_alloc (allocator,
        (GstGLAllocationParams *) raw->params);
    if (!tex) {
      gst_buffer_unref (*outbuf);
      *outbuf = NULL;
      GST_ERROR_OBJECT (raw->upload, "Failed to allocate wrapped texture");
      return GST_GL_UPLOAD_ERROR;
    }

    _raw_upload_frame_ref (raw->in_frame);
    gst_buffer_append_memory (*outbuf, (GstMemory *) tex);
  }
  gst_object_unref (allocator);

  _raw_upload_frame_unref (raw->in_frame);
  raw->in_frame = NULL;
  return GST_GL_UPLOAD_DONE;
}

static void
_raw_data_upload_free (gpointer impl)
{
  struct RawUpload *raw = impl;

  if (raw->params)
    gst_gl_allocation_params_free ((GstGLAllocationParams *) raw->params);

  g_free (raw);
}

static GstStaticCaps _raw_data_upload_caps =
GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE (GST_GL_MEMORY_VIDEO_FORMATS_STR));

static const UploadMethod _raw_data_upload = {
  "Raw Data",
  0,
  &_raw_data_upload_caps,
  &_raw_data_upload_new,
  &_raw_data_upload_transform_caps,
  &_raw_data_upload_accept,
  &_raw_data_upload_propose_allocation,
  &_raw_data_upload_perform,
  &_raw_data_upload_free
};

#if GST_GL_HAVE_VIV_DIRECTVIV
#ifndef GL_BGRA_EXT
#define GL_BGRA_EXT                                             0x80E1
#endif
#ifndef GL_VIV_YV12
#define GL_VIV_YV12                                             0x8FC0
#endif
#ifndef GL_VIV_NV12
#define GL_VIV_NV12                                             0x8FC1
#endif
#ifndef GL_VIV_YUY2
#define GL_VIV_YUY2                                             0x8FC2
#endif
#ifndef GL_VIV_UYVY
#define GL_VIV_UYVY                                             0x8FC3
#endif
#ifndef GL_VIV_NV21
#define GL_VIV_NV21                                             0x8FC4
#endif
#ifndef GL_VIV_I420
#define GL_VIV_I420                                             0x8FC5
#endif

struct DirectVIVUpload
{
  GstGLUpload *upload;

  GstGLVideoAllocationParams *params;
  GstBuffer *inbuf, *outbuf;
  void (*TexDirectVIVMap) (GLenum Target, GLsizei Width, GLsizei Height,
      GLenum Format, GLvoid ** Logical, const GLuint * Physical);
  void (*TexDirectInvalidateVIV) (GLenum Target);
  gboolean loaded_functions;
  GstBufferPool *pool;
};

#define GST_GL_DIRECTVIV_FORMAT "{RGBA, I420, YV12, NV12, NV21, YUY2, UYVY, BGRA, RGB16}"

static GstStaticCaps _directviv_upload_caps =
GST_STATIC_CAPS (GST_VIDEO_CAPS_MAKE (GST_GL_DIRECTVIV_FORMAT));

static gpointer
_directviv_upload_new (GstGLUpload * upload)
{
  struct DirectVIVUpload *directviv = g_new0 (struct DirectVIVUpload, 1);
  directviv->upload = upload;
  directviv->loaded_functions = FALSE;

  return directviv;
}

static gboolean
_directviv_upload_setup_buffer_pool (GstBufferPool **pool, GstAllocator *allocator,
    GstCaps *caps, GstVideoInfo *info)
{
  GstAllocationParams params;
  GstStructure *config;
  gsize size;
  guint width, height;
  GstVideoAlignment alignment;

  g_return_val_if_fail (caps != NULL && info != NULL, FALSE);

  width = GST_VIDEO_INFO_WIDTH (info);
  height = GST_VIDEO_INFO_HEIGHT (info);

  gst_allocation_params_init (&params);

  /* if user not provide an allocator, then use default physical allocator*/
  if (!allocator) {
#if GST_GL_HAVE_PHYMEM
    allocator = gst_phy_mem_allocator_obtain ();
#endif
  }

  if (!allocator) {
    GST_WARNING ("Cannot get available allocator");
    return FALSE;
  }
  GST_DEBUG ("got allocator(%p).", allocator);

  if (*pool)
    gst_object_unref(*pool);

  *pool = gst_video_buffer_pool_new ();
  if (!*pool) {
    GST_WARNING ("New video buffer pool failed.");
    return FALSE;
  }
  GST_DEBUG ("create buffer pool(%p).", *pool);

  config = gst_buffer_pool_get_config (*pool);

  /* configure alignment for eglimage to import this dma-fd buffer */
  memset (&alignment, 0, sizeof (GstVideoAlignment));
  alignment.padding_right = GST_ROUND_UP_N(width, DEFAULT_ALIGN) - width;
  GST_DEBUG ("align buffer pool, w(%d) h(%d), padding_right (%d), padding_bottom (%d)",
      width, height, alignment.padding_right, alignment.padding_bottom);

  /* the normal size of a frame */
  size = info->size;
  gst_buffer_pool_config_set_params (config, caps, size, 0, 30);
  gst_buffer_pool_config_add_option (config, GST_BUFFER_POOL_OPTION_VIDEO_META);
  gst_buffer_pool_config_add_option (config, GST_BUFFER_POOL_OPTION_VIDEO_ALIGNMENT);
  gst_buffer_pool_config_set_video_alignment (config, &alignment);
  gst_buffer_pool_config_set_allocator (config, allocator, &params);

  if (!gst_buffer_pool_set_config (*pool, config)) {
    GST_WARNING ("buffer pool config failed.");
    gst_object_unref (*pool);
    return FALSE;
  }

  return TRUE;
}

static GstCaps *
_directviv_upload_transform_caps (gpointer impl, GstGLContext * context,
    GstPadDirection direction, GstCaps * caps)
{
  GstCapsFeatures *passthrough =
      gst_caps_features_from_string
      (GST_CAPS_FEATURE_META_GST_VIDEO_OVERLAY_COMPOSITION);
  GstCaps *ret;

  if (direction == GST_PAD_SINK) {
    GstCaps *tmp;

    ret =
        _set_caps_features_with_passthrough (caps,
        GST_CAPS_FEATURE_MEMORY_GL_MEMORY, passthrough);

    gst_caps_set_simple (ret, "format", G_TYPE_STRING, "RGBA", NULL);
    tmp = _caps_intersect_texture_target (ret, 1 << GST_GL_TEXTURE_TARGET_2D);
    gst_caps_unref (ret);
    ret = tmp;
  } else {
    GstCaps *caps_copy, *caps_intersect;
    caps_copy = gst_caps_copy (caps);
    gst_caps_set_simple (caps_copy, "format", G_TYPE_STRING, "RGBA", NULL);
    caps_intersect = gst_caps_intersect (caps_copy, caps);
    if (gst_caps_is_empty (caps_intersect)) {
      ret =
          _set_caps_features_with_passthrough (caps,
          GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY, passthrough);
    } else {
      GstCaps *tmp;
      tmp = gst_caps_from_string (GST_VIDEO_CAPS_MAKE_WITH_FEATURES
        (GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY, GST_GL_DIRECTVIV_FORMAT));
      ret =
          _set_caps_features_with_passthrough (tmp,
          GST_CAPS_FEATURE_MEMORY_SYSTEM_MEMORY, passthrough);
      gst_caps_unref (tmp);
    }
    gst_caps_unref (caps_copy);
    gst_caps_unref (caps_intersect);
  }

  gst_caps_features_free (passthrough);
  return ret;
}

static gboolean
_directviv_upload_buffer_pool_is_ok (GstBufferPool * pool, GstCaps * newcaps,
    gint size)
{
  GstCaps *oldcaps;
  GstStructure *config;
  guint bsize;
  gboolean ret;

  config = gst_buffer_pool_get_config (pool);
  gst_buffer_pool_config_get_params (config, &oldcaps, &bsize, NULL, NULL);
  ret = (size <= bsize) && gst_caps_is_equal (newcaps, oldcaps);
  gst_structure_free (config);

  return ret;
}

static void
_directviv_upload_load_functions_gl_thread (GstGLContext * context,
    struct DirectVIVUpload *directviv)
{
  directviv->TexDirectVIVMap =
      gst_gl_context_get_proc_address (context, "glTexDirectVIVMap");
  directviv->TexDirectInvalidateVIV =
      gst_gl_context_get_proc_address (context, "glTexDirectInvalidateVIV");
}

static gboolean
_directviv_upload_accept (gpointer impl, GstBuffer * buffer, GstCaps * in_caps,
    GstCaps * out_caps)
{
  struct DirectVIVUpload *directviv = impl;
  GstCapsFeatures *features;
  guint n_mem;
  GstMemory *mem;

  if (!directviv->loaded_functions && (!directviv->TexDirectInvalidateVIV ||
          !directviv->TexDirectVIVMap)) {
    gst_gl_context_thread_add (directviv->upload->context,
        (GstGLContextThreadFunc) _directviv_upload_load_functions_gl_thread,
        directviv);
    directviv->loaded_functions = TRUE;
  }
  if (!directviv->TexDirectInvalidateVIV || !directviv->TexDirectVIVMap)
    return FALSE;

  features = gst_caps_get_features (out_caps, 0);
  if (!gst_caps_features_contains (features, GST_CAPS_FEATURE_MEMORY_GL_MEMORY))
    return FALSE;

  if (directviv->params)
    gst_gl_allocation_params_free ((GstGLAllocationParams *) directviv->params);
  if (!(directviv->params =
          gst_gl_video_allocation_params_new (directviv->upload->context, NULL,
              &directviv->upload->priv->out_info, -1, NULL,
              GST_GL_TEXTURE_TARGET_2D, GST_VIDEO_GL_TEXTURE_TYPE_RGBA)))
    return FALSE;

  /* We only support a single memory per buffer at this point */
  n_mem = gst_buffer_n_memory (buffer);
  if (n_mem == 1) {
    mem = gst_buffer_peek_memory (buffer, 0);
  } else {
    mem = NULL;
  }

#if GST_GL_HAVE_PHYMEM
  GstVideoInfo *in_info = &directviv->upload->priv->in_info;
  GstVideoFormat fmt = GST_VIDEO_INFO_FORMAT (&directviv->upload->priv->out_info);
  if (fmt != GST_VIDEO_FORMAT_RGBA)
    return FALSE;

  if (n_mem != 1 || !mem || !gst_is_phys_memory (mem)) {
    GstVideoFrame frame1, frame2;
    GstCaps *new_caps;
    GstVideoInfo info;

    gst_video_frame_map (&frame1, in_info, buffer, GST_MAP_READ);
    new_caps = gst_video_info_to_caps(&frame1.info);
    gst_video_info_from_caps(&info, new_caps);

    if (!directviv->pool || !_directviv_upload_buffer_pool_is_ok (directviv->pool,new_caps,info.size)) {
      gboolean ret;
      if (directviv->pool) {
        gst_object_unref(directviv->pool);
        directviv->pool = NULL;
      }

      ret = _directviv_upload_setup_buffer_pool (&directviv->pool, NULL, new_caps, in_info);
      if (!ret) {
        gst_video_frame_unmap (&frame1);
        gst_caps_unref (new_caps);
        GST_WARNING_OBJECT (directviv->upload, "no available buffer pool");
        return FALSE;
      }
    }

    if (!gst_buffer_pool_is_active (directviv->pool)
        && gst_buffer_pool_set_active (directviv->pool, TRUE) != TRUE) {
      gst_video_frame_unmap (&frame1);
      GST_WARNING_OBJECT (directviv->upload, "buffer pool is not ok");
      return FALSE;
    }

    if (directviv->inbuf)
      gst_buffer_unref(directviv->inbuf);
    directviv->inbuf = NULL;

    gst_buffer_pool_acquire_buffer (directviv->pool, &directviv->inbuf, NULL);
    if (!directviv->inbuf) {
      gst_video_frame_unmap (&frame1);
      GST_WARNING_OBJECT (directviv->upload, "acquire_buffer failed");
      return FALSE;
    }

    GST_DEBUG_OBJECT (directviv->upload, "copy plane resolution (%d)x(%d)\n", in_info->width, in_info->height);
    gst_video_frame_map (&frame2, in_info, directviv->inbuf, GST_MAP_WRITE);
    gst_video_frame_copy (&frame2, &frame1);
    gst_video_frame_unmap (&frame1);
    gst_video_frame_unmap (&frame2);
  }

  return TRUE;
#else
  return n_mem == 1 && mem && gst_is_phys_memory (mem);
#endif
}

static void
_directviv_upload_propose_allocation (gpointer impl, GstQuery * decide_query,
    GstQuery * query)
{
#if GST_GL_HAVE_PHYMEM
  struct DirectVIVUpload *directviv = impl;
  GstBufferPool *pool = NULL;
  GstAllocator *allocator = NULL;
  GstCaps *caps;
  GstVideoInfo info;
  GstVideoFormat fmt;

  fmt = GST_VIDEO_INFO_FORMAT (&directviv->upload->priv->out_info);

  if (fmt != GST_VIDEO_FORMAT_RGBA)
    return;

#if GST_GL_HAVE_IONDMA
  /* physical memory buffer pool was only proposed
   * when ion is not available to avoid allocator
   * overwrite in allocation query, we need keep use
   * ion when it is available */
  allocator = gst_ion_allocator_obtain ();
  if (allocator)
    return;
#endif

  gst_query_parse_allocation (query, &caps, NULL);

  if (!gst_video_info_from_caps (&info, caps))
    goto invalid_caps;

  allocator = gst_phy_mem_allocator_obtain ();
  if (!allocator) {
    GST_WARNING ("New physical memory allocator failed.");
    return;
  }
  GST_DEBUG ("create physical memory allocator(%p).", allocator);

  gst_query_add_allocation_param (query, allocator, NULL);

  if (!_directviv_upload_setup_buffer_pool (&pool, allocator, caps, &info))
    goto setup_failed;

  gst_query_set_nth_allocation_pool (query, 0, pool, info.size, 0, 30);

  if (pool)
    gst_object_unref (pool);

  return;
invalid_caps:
  {
    GST_WARNING_OBJECT (directviv->upload, "invalid caps specified");
    return;
  }
setup_failed:
  {
    GST_WARNING_OBJECT (directviv->upload, "failed to setup buffer pool");
    return;
  }
#endif
}

static GLenum
_directviv_upload_video_format_to_gl_format (GstVideoFormat format)
{
  switch (format) {
    case GST_VIDEO_FORMAT_I420:
      return GL_VIV_I420;
    case GST_VIDEO_FORMAT_YV12:
      return GL_VIV_YV12;
    case GST_VIDEO_FORMAT_NV12:
      return GL_VIV_NV12;
    case GST_VIDEO_FORMAT_NV21:
      return GL_VIV_NV21;
    case GST_VIDEO_FORMAT_YUY2:
      return GL_VIV_YUY2;
    case GST_VIDEO_FORMAT_UYVY:
      return GL_VIV_UYVY;
    case GST_VIDEO_FORMAT_RGB16:
      return GL_RGB565;
    case GST_VIDEO_FORMAT_RGBA:
      return GL_RGBA;
    case GST_VIDEO_FORMAT_BGRA:
      return GL_BGRA_EXT;
    case GST_VIDEO_FORMAT_RGBx:
      return GL_RGBA;
    case GST_VIDEO_FORMAT_BGRx:
      return GL_BGRA_EXT;
    default:
      return 0;
  }
}

typedef struct
{
  GstBuffer *buffer;
  GstMemory *memory;
  GstMapInfo map;
  guintptr phys_addr;
} DirectVIVUnmapData;

static void
_directviv_memory_unmap (DirectVIVUnmapData * data)
{
  gst_memory_unmap (data->memory, &data->map);
  gst_memory_unref (data->memory);
  gst_buffer_unref (data->buffer);
  g_free (data);
}

static void
_directviv_upload_perform_gl_thread (GstGLContext * context,
    struct DirectVIVUpload *directviv)
{
  static GQuark directviv_unmap_quark = 0;
  GstGLMemoryAllocator *allocator;
  GstMemory *in_mem;
  GstGLMemory *out_gl_mem;
  GstVideoInfo *in_info;
  DirectVIVUnmapData *unmap_data;
  GstVideoMeta *vmeta;
  gint width, height, gl_format;
  const GstGLFuncs *gl;

  if (!directviv_unmap_quark)
    directviv_unmap_quark = g_quark_from_static_string ("GstGLDirectVIVUnmap");

  gl = context->gl_vtable;

  g_assert (gst_buffer_n_memory (directviv->inbuf) == 1);
  in_info = &directviv->upload->priv->in_info;
  in_mem = gst_buffer_peek_memory (directviv->inbuf, 0);
  unmap_data = g_new0 (DirectVIVUnmapData, 1);
  if (!gst_memory_map (in_mem, &unmap_data->map, GST_MAP_READ)) {
    g_free (unmap_data);
    return;
  }
  unmap_data->phys_addr = gst_phys_memory_get_phys_addr (in_mem);
  if (!unmap_data->phys_addr) {
    gst_memory_unmap (in_mem, &unmap_data->map);
    g_free (unmap_data);
    return;
  }
  unmap_data->memory = gst_memory_ref (in_mem);
  unmap_data->buffer = gst_buffer_ref (directviv->inbuf);

  allocator =
      GST_GL_MEMORY_ALLOCATOR (gst_allocator_find
      (GST_GL_MEMORY_PBO_ALLOCATOR_NAME));

  /* FIXME: buffer pool */
  directviv->outbuf = gst_buffer_new ();
  gst_gl_memory_setup_buffer (allocator, directviv->outbuf, directviv->params,
      NULL, NULL, 0);
  gst_object_unref (allocator);

  out_gl_mem = (GstGLMemory *) gst_buffer_peek_memory (directviv->outbuf, 0);

  /* Need to keep the input memory and buffer mapped and valid until
   * the GL memory is not used anymore */
  gst_mini_object_set_qdata ((GstMiniObject *) out_gl_mem,
      directviv_unmap_quark, unmap_data,
      (GDestroyNotify) _directviv_memory_unmap);
  gst_buffer_add_parent_buffer_meta (directviv->outbuf, directviv->inbuf);

  /* width/height need to compensate for stride/padding */
  vmeta = gst_buffer_get_video_meta (directviv->inbuf);
  if (vmeta) {
    width = vmeta->stride[0];
    if (GST_VIDEO_INFO_N_PLANES (in_info) == 1)
      height = gst_memory_get_sizes (in_mem, NULL, NULL) / width;
    else
      height = vmeta->offset[1] / width;
  } else {
    width = GST_VIDEO_INFO_PLANE_STRIDE (in_info, 0);
    if (GST_VIDEO_INFO_N_PLANES (in_info) == 1)
      height = gst_memory_get_sizes (in_mem, NULL, NULL) / width;
    else
      height = GST_VIDEO_INFO_PLANE_OFFSET (in_info, 1) / width;
  }
  width /= GST_VIDEO_INFO_COMP_PSTRIDE (in_info, 0);

  gl_format =
      _directviv_upload_video_format_to_gl_format (GST_VIDEO_INFO_FORMAT
      (in_info));

  gl->BindTexture (GL_TEXTURE_2D, out_gl_mem->tex_id);
  directviv->TexDirectVIVMap (GL_TEXTURE_2D, width, height,
      gl_format, (void **) &unmap_data->map.data, &unmap_data->phys_addr);
  directviv->TexDirectInvalidateVIV (GL_TEXTURE_2D);
}

static GstGLUploadReturn
_directviv_upload_perform (gpointer impl, GstBuffer * buffer,
    GstBuffer ** outbuf)
{
  struct DirectVIVUpload *directviv = impl;

  if (!directviv->inbuf)
    directviv->inbuf = buffer;
  directviv->outbuf = NULL;
  gst_gl_context_thread_add (directviv->upload->context,
      (GstGLContextThreadFunc) _directviv_upload_perform_gl_thread, directviv);

  if (directviv->inbuf == buffer)
    directviv->inbuf = NULL;

  if (!directviv->outbuf)
    return GST_GL_UPLOAD_ERROR;

  *outbuf = directviv->outbuf;
  directviv->outbuf = NULL;

  return GST_GL_UPLOAD_DONE;
}

static void
_directviv_upload_free (gpointer impl)
{
  struct DirectVIVUpload *directviv = impl;

  if (directviv->params)
    gst_gl_allocation_params_free ((GstGLAllocationParams *) directviv->params);

  g_free (impl);
}

static const UploadMethod _directviv_upload = {
  "DirectVIV",
  0,
  &_directviv_upload_caps,
  &_directviv_upload_new,
  &_directviv_upload_transform_caps,
  &_directviv_upload_accept,
  &_directviv_upload_propose_allocation,
  &_directviv_upload_perform,
  &_directviv_upload_free
};

#endif /* GST_GL_HAVE_VIV_DIRECTVIV */

static const UploadMethod *upload_methods[] = { &_gl_memory_upload,
#if GST_GL_HAVE_DMABUF
  &_dma_buf_upload,
#endif
#if GST_GL_HAVE_VIV_DIRECTVIV
  &_directviv_upload,
#endif
  &_upload_meta_upload, &_raw_data_upload
};

static GMutex upload_global_lock;

GstCaps *
gst_gl_upload_get_input_template_caps (void)
{
  GstCaps *ret = NULL;
  gint i;

  g_mutex_lock (&upload_global_lock);

  /* FIXME: cache this and invalidate on changes to upload_methods */
  for (i = 0; i < G_N_ELEMENTS (upload_methods); i++) {
    GstCaps *template =
        gst_static_caps_get (upload_methods[i]->input_template_caps);
    ret = ret == NULL ? template : gst_caps_merge (ret, template);
  }

  ret = gst_caps_simplify (ret);
  ret = gst_gl_overlay_compositor_add_caps (ret);
  g_mutex_unlock (&upload_global_lock);

  return ret;
}

static void
gst_gl_upload_class_init (GstGLUploadClass * klass)
{
  g_type_class_add_private (klass, sizeof (GstGLUploadPrivate));

  G_OBJECT_CLASS (klass)->finalize = gst_gl_upload_finalize;
}

static void
gst_gl_upload_init (GstGLUpload * upload)
{
  upload->priv = GST_GL_UPLOAD_GET_PRIVATE (upload);
}

/**
 * gst_gl_upload_new:
 * @context: a #GstGLContext
 *
 * Returns: (transfer full): a new #GstGLUpload object
 */
GstGLUpload *
gst_gl_upload_new (GstGLContext * context)
{
  GstGLUpload *upload = g_object_new (GST_TYPE_GL_UPLOAD, NULL);
  gint i, n;

  gst_object_ref_sink (upload);

  if (context)
    gst_gl_upload_set_context (upload, context);
  else
    upload->context = NULL;

  n = G_N_ELEMENTS (upload_methods);
  upload->priv->upload_impl = g_malloc (sizeof (gpointer) * n);
  for (i = 0; i < n; i++) {
    upload->priv->upload_impl[i] = upload_methods[i]->new (upload);
  }

  GST_DEBUG_OBJECT (upload, "Created new GLUpload for context %" GST_PTR_FORMAT,
      context);

  return upload;
}

void
gst_gl_upload_set_context (GstGLUpload * upload, GstGLContext * context)
{
  g_return_if_fail (upload != NULL);

  gst_object_replace ((GstObject **) & upload->context, (GstObject *) context);
}

static void
gst_gl_upload_finalize (GObject * object)
{
  GstGLUpload *upload;
  gint i, n;

  upload = GST_GL_UPLOAD (object);

  upload->priv->method_i = 0;

  if (upload->context) {
    gst_object_unref (upload->context);
    upload->context = NULL;
  }

  if (upload->priv->in_caps) {
    gst_caps_unref (upload->priv->in_caps);
    upload->priv->in_caps = NULL;
  }

  if (upload->priv->out_caps) {
    gst_caps_unref (upload->priv->out_caps);
    upload->priv->out_caps = NULL;
  }

  n = G_N_ELEMENTS (upload_methods);
  for (i = 0; i < n; i++) {
    if (upload->priv->upload_impl[i])
      upload_methods[i]->free (upload->priv->upload_impl[i]);
  }
  g_free (upload->priv->upload_impl);

  G_OBJECT_CLASS (gst_gl_upload_parent_class)->finalize (object);
}

GstCaps *
gst_gl_upload_transform_caps (GstGLUpload * upload, GstGLContext * context,
    GstPadDirection direction, GstCaps * caps, GstCaps * filter)
{
  GstCaps *result, *tmp;
  gint i;

  tmp = gst_caps_new_empty ();

  for (i = 0; i < G_N_ELEMENTS (upload_methods); i++) {
    GstCaps *tmp2;

    tmp2 =
        upload_methods[i]->transform_caps (upload->priv->upload_impl[i],
        context, direction, caps);

    if (tmp2)
      tmp = gst_caps_merge (tmp, tmp2);
  }

  if (filter) {
    result = gst_caps_intersect_full (tmp, filter, GST_CAPS_INTERSECT_FIRST);
    gst_caps_unref (tmp);
  } else {
    result = tmp;
  }

  return result;
}

/**
 * gst_gl_upload_propose_allocation:
 * @upload: a #GstGLUpload
 * @decide_query: (allow-none): a #GstQuery from a decide allocation
 * @query: the proposed allocation query
 *
 * Adds the required allocation parameters to support uploading.
 */
void
gst_gl_upload_propose_allocation (GstGLUpload * upload, GstQuery * decide_query,
    GstQuery * query)
{
  gint i;

  for (i = 0; i < G_N_ELEMENTS (upload_methods); i++)
    upload_methods[i]->propose_allocation (upload->priv->upload_impl[i],
        decide_query, query);
}

static gboolean
_gst_gl_upload_set_caps_unlocked (GstGLUpload * upload, GstCaps * in_caps,
    GstCaps * out_caps)
{
  g_return_val_if_fail (upload != NULL, FALSE);
  g_return_val_if_fail (gst_caps_is_fixed (in_caps), FALSE);

  if (upload->priv->in_caps && upload->priv->out_caps
      && gst_caps_is_equal (upload->priv->in_caps, in_caps)
      && gst_caps_is_equal (upload->priv->out_caps, out_caps))
    return TRUE;

  gst_caps_replace (&upload->priv->in_caps, in_caps);
  gst_caps_replace (&upload->priv->out_caps, out_caps);

  gst_video_info_from_caps (&upload->priv->in_info, in_caps);
  gst_video_info_from_caps (&upload->priv->out_info, out_caps);

  upload->priv->method_impl = NULL;
  upload->priv->method_i = 0;

  return TRUE;
}

/**
 * gst_gl_upload_set_caps:
 * @upload: a #GstGLUpload
 * @in_caps: input #GstCaps
 * @out_caps: output #GstCaps
 *
 * Initializes @upload with the information required for upload.
 *
 * Returns: whether @in_caps and @out_caps could be set on @upload
 */
gboolean
gst_gl_upload_set_caps (GstGLUpload * upload, GstCaps * in_caps,
    GstCaps * out_caps)
{
  gboolean ret;

  GST_OBJECT_LOCK (upload);
  ret = _gst_gl_upload_set_caps_unlocked (upload, in_caps, out_caps);
  GST_OBJECT_UNLOCK (upload);

  return ret;
}

/**
 * gst_gl_upload_get_caps:
 * @upload: a #GstGLUpload
 * @in_caps: (transfer full) (allow-none) (out): the input #GstCaps
 * @out_caps: (transfer full) (allow-none) (out): the output #GstCaps
 */
void
gst_gl_upload_get_caps (GstGLUpload * upload, GstCaps ** in_caps,
    GstCaps ** out_caps)
{
  GST_OBJECT_LOCK (upload);
  if (in_caps)
    *in_caps =
        upload->priv->in_caps ? gst_caps_ref (upload->priv->in_caps) : NULL;
  if (out_caps)
    *out_caps =
        upload->priv->out_caps ? gst_caps_ref (upload->priv->out_caps) : NULL;
  GST_OBJECT_UNLOCK (upload);
}

static gboolean
_upload_find_method (GstGLUpload * upload)
{
  gint method_i;

  if (upload->priv->method_i >= G_N_ELEMENTS (upload_methods))
    return FALSE;

  method_i = upload->priv->method_i;
  upload->priv->method = upload_methods[method_i];
  upload->priv->method_impl = upload->priv->upload_impl[method_i];

  GST_DEBUG_OBJECT (upload, "attempting upload with uploader %s",
      upload->priv->method->name);

  upload->priv->method_i++;

  return TRUE;
}

/**
 * gst_gl_upload_perform_with_buffer:
 * @upload: a #GstGLUpload
 * @buffer: input #GstBuffer
 * @outbuf_ptr: (out): resulting #GstBuffer
 *
 * Uploads @buffer using the transformation specified by
 * gst_gl_upload_set_caps() creating a new #GstBuffer in @outbuf_ptr.
 *
 * Returns: whether the upload was successful
 */
GstGLUploadReturn
gst_gl_upload_perform_with_buffer (GstGLUpload * upload, GstBuffer * buffer,
    GstBuffer ** outbuf_ptr)
{
  GstGLUploadReturn ret = GST_GL_UPLOAD_ERROR;
  GstBuffer *outbuf;

  g_return_val_if_fail (GST_IS_GL_UPLOAD (upload), FALSE);
  g_return_val_if_fail (GST_IS_BUFFER (buffer), FALSE);
  g_return_val_if_fail (outbuf_ptr != NULL, FALSE);

  GST_OBJECT_LOCK (upload);

#define NEXT_METHOD \
do { \
  if (!_upload_find_method (upload)) { \
    GST_OBJECT_UNLOCK (upload); \
    return FALSE; \
  } \
  goto restart; \
} while (0)

  if (!upload->priv->method_impl)
    _upload_find_method (upload);

restart:
  if (!upload->priv->method->accept (upload->priv->method_impl, buffer,
          upload->priv->in_caps, upload->priv->out_caps))
    NEXT_METHOD;

  ret =
      upload->priv->method->perform (upload->priv->method_impl, buffer,
      &outbuf);
  if (ret == GST_GL_UPLOAD_UNSHARED_GL_CONTEXT) {
    gint i;

    for (i = 0; i < G_N_ELEMENTS (upload_methods); i++) {
      if (upload_methods[i] == &_raw_data_upload) {
        upload->priv->method = &_raw_data_upload;
        upload->priv->method_impl = upload->priv->upload_impl[i];
        upload->priv->method_i = i;

        break;
      }
    }
    goto restart;
  } else if (ret == GST_GL_UPLOAD_DONE || ret == GST_GL_UPLOAD_RECONFIGURE) {
    /* we are done */
  } else {
    upload->priv->method_impl = NULL;
    NEXT_METHOD;
  }

  if (outbuf && buffer != outbuf)
    gst_buffer_copy_into (outbuf, buffer,
        GST_BUFFER_COPY_FLAGS | GST_BUFFER_COPY_TIMESTAMPS, 0, -1);
  *outbuf_ptr = outbuf;

  GST_OBJECT_UNLOCK (upload);

  return ret;

#undef NEXT_METHOD
}
