Example #1
0
bool VaapiSurfaceGLXImpl::update(boost::shared_ptr<VaapiSurface> surface)
{
    GNASH_REPORT_FUNCTION;

    if (!this->surface()) {
        return false;
    }

    VaapiGlobalContext * gvactx = VaapiGlobalContext::get();
    if (!gvactx) {
        return false;
    }

    VAStatus status;
    status = vaSyncSurface(gvactx->display(), surface->get());
    if (!vaapi_check_status(status, "vaSyncSurface()"))
        return false;

    status = vaCopySurfaceGLX(gvactx->display(), this->surface(),
                              surface->get(), VA_FRAME_PICTURE);
    if (!vaapi_check_status(status, "vaCopySurfaceGLX()")) {
        return false;
    }

    return true;
}
Example #2
0
bool
VaapiGlobalContext::init()
{
    GNASH_REPORT_FUNCTION;

    VADisplay dpy = display();
    VAStatus status;

    int num_profiles = 0;
    _profiles.resize(vaMaxNumProfiles(dpy));
    status = vaQueryConfigProfiles(dpy, &_profiles[0], &num_profiles);
    if (!vaapi_check_status(status, "vaQueryConfigProfiles()")) {
        return false;
    }
    _profiles.resize(num_profiles);

    int num_image_formats = 0;
    _image_formats.resize(vaMaxNumImageFormats(dpy));
    status = vaQueryImageFormats(dpy, &_image_formats[0], &num_image_formats);
    if (!vaapi_check_status(status, "vaQueryImageFormats()")) {
        return false;
    }
    _image_formats.resize(num_image_formats);

    unsigned int num_subpicture_formats = 0;
    std::vector<unsigned int> flags;
    flags.resize(vaMaxNumSubpictureFormats(dpy));
    _subpicture_formats.resize(vaMaxNumSubpictureFormats(dpy));
    status = vaQuerySubpictureFormats(dpy, &_subpicture_formats[0], &flags[0], &num_subpicture_formats);
    if (!vaapi_check_status(status, "vaQuerySubpictureFormats()")) {
        return false;
    }
    _subpicture_formats.resize(num_subpicture_formats);
    return true;
}
Example #3
0
static int has_entrypoint(VAAPIContext *vaapi, VAProfile profile, VAEntrypoint entrypoint)
{
    VAStatus status;
    int i;

    if (!vaapi->entrypoints || vaapi->n_entrypoints == 0) {
        vaapi->entrypoints = calloc(vaMaxNumEntrypoints(vaapi->display), sizeof(vaapi->entrypoints[0]));

        status = vaQueryConfigEntrypoints(vaapi->display, profile,
                                          vaapi->entrypoints,
                                          &vaapi->n_entrypoints);
        if (!vaapi_check_status(status, "vaQueryConfigEntrypoints()"))
            return 0;

        D(bug("%d entrypoints available for %s\n", vaapi->n_entrypoints,
              string_of_VAProfile(profile)));
        for (i = 0; i < vaapi->n_entrypoints; i++)
            D(bug("  %s\n", string_of_VAEntrypoint(vaapi->entrypoints[i])));
    }

    for (i = 0; i < vaapi->n_entrypoints; i++) {
        if (vaapi->entrypoints[i] == entrypoint)
            return 1;
    }
    return 0;
}
Example #4
0
static int has_profile(VAAPIContext *vaapi, VAProfile profile)
{
    VAStatus status;
    int i;

    if (!vaapi->profiles || vaapi->n_profiles == 0) {
        vaapi->profiles = calloc(vaMaxNumProfiles(vaapi->display), sizeof(vaapi->profiles[0]));

        status = vaQueryConfigProfiles(vaapi->display,
                                       vaapi->profiles,
                                       &vaapi->n_profiles);
        if (!vaapi_check_status(status, "vaQueryConfigProfiles()"))
            return 0;

        D(bug("%d profiles available\n", vaapi->n_profiles));
        for (i = 0; i < vaapi->n_profiles; i++)
            D(bug("  %s\n", string_of_VAProfile(vaapi->profiles[i])));
    }

    for (i = 0; i < vaapi->n_profiles; i++) {
        if (vaapi->profiles[i] == profile)
            return 1;
    }
    return 0;
}
Example #5
0
gboolean
_gst_vaapi_image_unmap(GstVaapiImage *image)
{
    GstVaapiDisplay *display;
    VAStatus status;

    if (!_gst_vaapi_image_is_mapped(image))
        return FALSE;

    display = GST_VAAPI_OBJECT_DISPLAY(image);
    if (!display)
        return FALSE;

    GST_VAAPI_DISPLAY_LOCK(display);
    status = vaUnmapBuffer(
        GST_VAAPI_DISPLAY_VADISPLAY(display),
        image->priv->image.buf
    );
    GST_VAAPI_DISPLAY_UNLOCK(display);
    if (!vaapi_check_status(status, "vaUnmapBuffer()"))
        return FALSE;

    image->priv->image_data = NULL;
    return TRUE;
}
static void
gst_vaapi_subpicture_destroy (GstVaapiSubpicture * subpicture)
{
  GstVaapiDisplay *const display = GST_VAAPI_OBJECT_DISPLAY (subpicture);
  VASubpictureID subpicture_id;
  VAStatus status;

  subpicture_id = GST_VAAPI_OBJECT_ID (subpicture);
  GST_DEBUG ("subpicture %" GST_VAAPI_ID_FORMAT,
      GST_VAAPI_ID_ARGS (subpicture_id));

  if (subpicture_id != VA_INVALID_ID) {
    if (display) {
      GST_VAAPI_DISPLAY_LOCK (display);
      status = vaDestroySubpicture (GST_VAAPI_DISPLAY_VADISPLAY (display),
          subpicture_id);
      GST_VAAPI_DISPLAY_UNLOCK (display);
      if (!vaapi_check_status (status, "vaDestroySubpicture()"))
        g_warning ("failed to destroy subpicture %" GST_VAAPI_ID_FORMAT,
            GST_VAAPI_ID_ARGS (subpicture_id));
    }
    GST_VAAPI_OBJECT_ID (subpicture) = VA_INVALID_ID;
  }
  gst_vaapi_object_replace (&subpicture->image, NULL);
}
static gboolean
gst_vaapi_surface_create (GstVaapiSurface * surface,
    GstVaapiChromaType chroma_type, guint width, guint height)
{
  GstVaapiDisplay *const display = GST_VAAPI_OBJECT_DISPLAY (surface);
  VASurfaceID surface_id;
  VAStatus status;
  guint va_chroma_format;

  va_chroma_format = from_GstVaapiChromaType (chroma_type);
  if (!va_chroma_format)
    goto error_unsupported_chroma_type;

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaCreateSurfaces (GST_VAAPI_DISPLAY_VADISPLAY (display),
      width, height, va_chroma_format, 1, &surface_id);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaCreateSurfaces()"))
    return FALSE;

  surface->format = GST_VIDEO_FORMAT_UNKNOWN;
  surface->chroma_type = chroma_type;
  surface->width = width;
  surface->height = height;

  GST_DEBUG ("surface %" GST_VAAPI_ID_FORMAT, GST_VAAPI_ID_ARGS (surface_id));
  GST_VAAPI_OBJECT_ID (surface) = surface_id;
  return TRUE;

  /* ERRORS */
error_unsupported_chroma_type:
  GST_ERROR ("unsupported chroma-type %u", chroma_type);
  return FALSE;
}
/**
 * gst_vaapi_subpicture_set_global_alpha:
 * @subpicture: a #GstVaapiSubpicture
 * @global_alpha: value for global-alpha (range: 0.0 to 1.0, inclusive)
 *
 * Sets the global_alpha value of @subpicture. This function calls
 * vaSetSubpictureGlobalAlpha() if the format of @subpicture, i.e.
 * the current VA driver supports it.
 *
 * Return value: %TRUE if global_alpha could be set, %FALSE otherwise
 */
gboolean
gst_vaapi_subpicture_set_global_alpha (GstVaapiSubpicture * subpicture,
    gfloat global_alpha)
{
  GstVaapiDisplay *display;
  VAStatus status;

  g_return_val_if_fail (subpicture != NULL, FALSE);

  if (!(subpicture->flags & GST_VAAPI_SUBPICTURE_FLAG_GLOBAL_ALPHA))
    return FALSE;

  if (subpicture->global_alpha == global_alpha)
    return TRUE;

  display = GST_VAAPI_OBJECT_DISPLAY (subpicture);

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaSetSubpictureGlobalAlpha (GST_VAAPI_DISPLAY_VADISPLAY (display),
      GST_VAAPI_OBJECT_ID (subpicture), global_alpha);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaSetSubpictureGlobalAlpha()"))
    return FALSE;

  subpicture->global_alpha = global_alpha;
  return TRUE;
}
/**
 * gst_vaapi_surface_derive_image:
 * @surface: a #GstVaapiSurface
 *
 * Derives a #GstVaapiImage from the @surface. This image buffer can
 * then be mapped/unmapped for direct CPU access. This operation is
 * only possible if the underlying implementation supports direct
 * rendering capabilities and internal surface formats that can be
 * represented with a #GstVaapiImage.
 *
 * When the operation is not possible, the function returns %NULL and
 * the user should then fallback to using gst_vaapi_surface_get_image()
 * or gst_vaapi_surface_put_image() to accomplish the same task in an
 * indirect manner (additional copy).
 *
 * An image created with gst_vaapi_surface_derive_image() should be
 * unreferenced when it's no longer needed. The image and image buffer
 * data structures will be destroyed. However, the surface contents
 * will remain unchanged until destroyed through the last call to
 * gst_vaapi_object_unref().
 *
 * Return value: the newly allocated #GstVaapiImage object, or %NULL
 *   on failure
 */
GstVaapiImage *
gst_vaapi_surface_derive_image (GstVaapiSurface * surface)
{
  GstVaapiDisplay *display;
  VAImage va_image;
  VAStatus status;
  GstVaapiImage *image;

  g_return_val_if_fail (surface != NULL, NULL);

  display = GST_VAAPI_OBJECT_DISPLAY (surface);
  va_image.image_id = VA_INVALID_ID;
  va_image.buf = VA_INVALID_ID;

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaDeriveImage (GST_VAAPI_DISPLAY_VADISPLAY (display),
      GST_VAAPI_OBJECT_ID (surface), &va_image);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaDeriveImage()"))
    return NULL;
  if (va_image.image_id == VA_INVALID_ID || va_image.buf == VA_INVALID_ID)
    return NULL;

  image = gst_vaapi_image_new_with_image (display, &va_image);
  if (!image)
    vaDestroyImage (GST_VAAPI_DISPLAY_VADISPLAY (display), va_image.image_id);
  return image;
}
/* Creates and maps VA buffer */
gboolean
vaapi_create_buffer (VADisplay dpy, VAContextID ctx, int type, guint size,
    gconstpointer buf, VABufferID * buf_id_ptr, gpointer * mapped_data)
{
  VABufferID buf_id;
  VAStatus status;
  gpointer data = (gpointer) buf;

  status = vaCreateBuffer (dpy, ctx, type, size, 1, data, &buf_id);
  if (!vaapi_check_status (status, "vaCreateBuffer()"))
    return FALSE;

  if (mapped_data) {
    data = vaapi_map_buffer (dpy, buf_id);
    if (!data)
      goto error;
    *mapped_data = data;
  }

  *buf_id_ptr = buf_id;
  return TRUE;

error:
  vaapi_destroy_buffer (dpy, &buf_id);
  return FALSE;
}
Example #11
0
/**
 * gst_vaapi_surface_query_status:
 * @surface: a #GstVaapiSurface
 * @pstatus: return location for the #GstVaapiSurfaceStatus
 *
 * Finds out any pending operations on the @surface. The
 * #GstVaapiSurfaceStatus flags are returned into @pstatus.
 *
 * Return value: %TRUE on success
 */
gboolean
gst_vaapi_surface_query_status(
    GstVaapiSurface       *surface,
    GstVaapiSurfaceStatus *pstatus
)
{
    VASurfaceStatus surface_status;
    VAStatus status;

    g_return_val_if_fail(GST_VAAPI_IS_SURFACE(surface), FALSE);

    GST_VAAPI_OBJECT_LOCK_DISPLAY(surface);
    status = vaQuerySurfaceStatus(
        GST_VAAPI_OBJECT_VADISPLAY(surface),
        GST_VAAPI_OBJECT_ID(surface),
        &surface_status
    );
    GST_VAAPI_OBJECT_UNLOCK_DISPLAY(surface);
    if (!vaapi_check_status(status, "vaQuerySurfaceStatus()"))
        return FALSE;

    if (pstatus)
        *pstatus = to_GstVaapiSurfaceStatus(surface_status);
    return TRUE;
}
Example #12
0
VaapiSurfaceGLXImpl::VaapiSurfaceGLXImpl(GLenum target, GLuint texture)
    : VaapiSurfaceImplBase(0, 0)
{
    GNASH_REPORT_FUNCTION;

    reset(0);

    if (target == 0 || texture == 0) {
        return;
    }

    VaapiGlobalContext * gvactx = VaapiGlobalContext::get();
    if (!gvactx) {
        return;
    }

    VAStatus status;
    void *surface = NULL;
    status = vaCreateSurfaceGLX(gvactx->display(), target, texture, &surface);
    if (!vaapi_check_status(status, "vaCreateSurfaceGLX()")) {
        return;
    }

    reset(reinterpret_cast<uintptr_t>(surface));

    log_debug(_("  -> surface %p\n", this->surface()));
}
/**
 * gst_vaapi_surface_put_image:
 * @surface: a #GstVaapiSurface
 * @image: a #GstVaapiImage
 *
 * Copies data from a #GstVaapiImage into a @surface. The @image must
 * have a format supported by the @surface.
 *
 * Return value: %TRUE on success
 */
gboolean
gst_vaapi_surface_put_image (GstVaapiSurface * surface, GstVaapiImage * image)
{
  GstVaapiDisplay *display;
  VAImageID image_id;
  VAStatus status;
  guint width, height;

  g_return_val_if_fail (surface != NULL, FALSE);
  g_return_val_if_fail (image != NULL, FALSE);

  display = GST_VAAPI_OBJECT_DISPLAY (surface);
  if (!display)
    return FALSE;

  width = GST_VAAPI_IMAGE_WIDTH (image);
  height = GST_VAAPI_IMAGE_HEIGHT (image);
  if (width != surface->width || height != surface->height)
    return FALSE;

  image_id = GST_VAAPI_OBJECT_ID (image);
  if (image_id == VA_INVALID_ID)
    return FALSE;

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaPutImage (GST_VAAPI_DISPLAY_VADISPLAY (display),
      GST_VAAPI_OBJECT_ID (surface), image_id, 0, 0, width, height,
      0, 0, width, height);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaPutImage()"))
    return FALSE;

  return TRUE;
}
gboolean
_gst_vaapi_surface_deassociate_subpicture (GstVaapiSurface * surface,
    GstVaapiSubpicture * subpicture)
{
  GstVaapiDisplay *display;
  VASurfaceID surface_id;
  VAStatus status;

  display = GST_VAAPI_OBJECT_DISPLAY (surface);
  if (!display)
    return FALSE;

  surface_id = GST_VAAPI_OBJECT_ID (surface);
  if (surface_id == VA_INVALID_SURFACE)
    return FALSE;

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaDeassociateSubpicture (GST_VAAPI_DISPLAY_VADISPLAY (display),
      GST_VAAPI_OBJECT_ID (subpicture), &surface_id, 1);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaDeassociateSubpicture()"))
    return FALSE;

  return TRUE;
}
static void
gst_vaapi_surface_destroy (GstVaapiSurface * surface)
{
  GstVaapiDisplay *const display = GST_VAAPI_OBJECT_DISPLAY (surface);
  VASurfaceID surface_id;
  VAStatus status;

  surface_id = GST_VAAPI_OBJECT_ID (surface);
  GST_DEBUG ("surface %" GST_VAAPI_ID_FORMAT, GST_VAAPI_ID_ARGS (surface_id));

  gst_vaapi_surface_destroy_subpictures (surface);
  gst_vaapi_surface_set_parent_context (surface, NULL);

  if (surface_id != VA_INVALID_SURFACE) {
    GST_VAAPI_DISPLAY_LOCK (display);
    status = vaDestroySurfaces (GST_VAAPI_DISPLAY_VADISPLAY (display),
        &surface_id, 1);
    GST_VAAPI_DISPLAY_UNLOCK (display);
    if (!vaapi_check_status (status, "vaDestroySurfaces()"))
      g_warning ("failed to destroy surface %" GST_VAAPI_ID_FORMAT,
          GST_VAAPI_ID_ARGS (surface_id));
    GST_VAAPI_OBJECT_ID (surface) = VA_INVALID_SURFACE;
  }
  gst_vaapi_buffer_proxy_replace (&surface->extbuf_proxy, NULL);
}
Example #16
0
gboolean
_gst_vaapi_surface_associate_subpicture(
    GstVaapiSurface         *surface,
    GstVaapiSubpicture      *subpicture,
    const GstVaapiRectangle *src_rect,
    const GstVaapiRectangle *dst_rect
)
{
    GstVaapiDisplay *display;
    GstVaapiRectangle src_rect_default, dst_rect_default;
    GstVaapiImage *image;
    VASurfaceID surface_id;
    VAStatus status;

    display = GST_VAAPI_OBJECT_DISPLAY(surface);
    if (!display)
        return FALSE;

    surface_id = GST_VAAPI_OBJECT_ID(surface);
    if (surface_id == VA_INVALID_SURFACE)
        return FALSE;

    if (!src_rect) {
        image = gst_vaapi_subpicture_get_image(subpicture);
        if (!image)
            return FALSE;
        src_rect                = &src_rect_default;
        src_rect_default.x      = 0;
        src_rect_default.y      = 0;
        gst_vaapi_image_get_size(
            image,
            &src_rect_default.width,
            &src_rect_default.height
        );
    }

    if (!dst_rect) {
        dst_rect                = &dst_rect_default;
        dst_rect_default.x      = 0;
        dst_rect_default.y      = 0;
        dst_rect_default.width  = surface->priv->width;
        dst_rect_default.height = surface->priv->height;
    }

    GST_VAAPI_DISPLAY_LOCK(display);
    status = vaAssociateSubpicture(
        GST_VAAPI_DISPLAY_VADISPLAY(display),
        GST_VAAPI_OBJECT_ID(subpicture),
        &surface_id, 1,
        src_rect->x, src_rect->y, src_rect->width, src_rect->height,
        dst_rect->x, dst_rect->y, dst_rect->width, dst_rect->height,
        0
    );
    GST_VAAPI_DISPLAY_UNLOCK(display);
    if (!vaapi_check_status(status, "vaAssociateSubpicture()"))
        return FALSE;

    return TRUE;
}
Example #17
0
static void *alloc_buffer(VAAPIContext *vaapi, int type, unsigned int size, VABufferID *buf_id)
{
    VAStatus status;
    void *data = NULL;

    *buf_id = 0;
    status = vaCreateBuffer(vaapi->display, vaapi->context_id,
                            type, size, 1, NULL, buf_id);
    if (!vaapi_check_status(status, "vaCreateBuffer()"))
        return NULL;

    status = vaMapBuffer(vaapi->display, *buf_id, &data);
    if (!vaapi_check_status(status, "vaMapBuffer()"))
        return NULL;

    return data;
}
Example #18
0
static int release_image(VAImage *va_image)
{
    VAAPIContext * const vaapi = vaapi_get_context();
    VAStatus status;

    status = vaUnmapBuffer(vaapi->display, va_image->buf);
    if (!vaapi_check_status(status, "vaUnmapBuffer()"))
        return -1;
    return 0;
}
/* Maps VA buffer */
gpointer
vaapi_map_buffer (VADisplay dpy, VABufferID buf_id)
{
  VAStatus status;
  gpointer data = NULL;

  status = vaMapBuffer (dpy, buf_id, &data);
  if (!vaapi_check_status (status, "vaMapBuffer()"))
    return NULL;
  return data;
}
/* Unmaps VA buffer */
void
vaapi_unmap_buffer (VADisplay dpy, VABufferID buf_id, gpointer * pbuf)
{
  VAStatus status;

  if (pbuf)
    *pbuf = NULL;

  status = vaUnmapBuffer (dpy, buf_id);
  if (!vaapi_check_status (status, "vaUnmapBuffer()"))
    return;
}
Example #21
0
gboolean
_gst_vaapi_image_map(GstVaapiImage *image, GstVaapiImageRaw *raw_image)
{
    GstVaapiImagePrivate * const priv = image->priv;
    GstVaapiDisplay *display;
    void *image_data;
    VAStatus status;
    guint i;

    if (_gst_vaapi_image_is_mapped(image))
        return TRUE;

    display = GST_VAAPI_OBJECT_DISPLAY(image);
    if (!display)
        return FALSE;

    GST_VAAPI_DISPLAY_LOCK(display);
    status = vaMapBuffer(
        GST_VAAPI_DISPLAY_VADISPLAY(display),
        image->priv->image.buf,
        &image_data
    );
    GST_VAAPI_DISPLAY_UNLOCK(display);
    if (!vaapi_check_status(status, "vaMapBuffer()"))
        return FALSE;

    image->priv->image_data = image_data;

    if (raw_image) {
        const VAImage * const va_image = &priv->image;
        raw_image->format     = priv->format;
        raw_image->width      = va_image->width;
        raw_image->height     = va_image->height;
        raw_image->num_planes = va_image->num_planes;
        for (i = 0; i < raw_image->num_planes; i++) {
            raw_image->pixels[i] = (guchar *)image_data + va_image->offsets[i];
            raw_image->stride[i] = va_image->pitches[i];
        }
    }
    return TRUE;
}
Example #22
0
bool VaapiDisplay::init()
{
    GNASH_REPORT_FUNCTION;

    VAStatus status;
    int major_version, minor_version;

    if (!_display) {
        return false;
    }

    status = vaInitialize(_display, &major_version, &minor_version);

    if (!vaapi_check_status(status, "vaInitialize()")) {
        return false;
    }

    vaapi_dprintf("VA API version %d.%d\n", major_version, minor_version);

    return true;
}
/**
 * gst_vaapi_surface_sync:
 * @surface: a #GstVaapiSurface
 *
 * Blocks until all pending operations on the @surface have been
 * completed.
 *
 * Return value: %TRUE on success
 */
gboolean
gst_vaapi_surface_sync (GstVaapiSurface * surface)
{
  GstVaapiDisplay *display;
  VAStatus status;

  g_return_val_if_fail (surface != NULL, FALSE);

  display = GST_VAAPI_OBJECT_DISPLAY (surface);
  if (!display)
    return FALSE;

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaSyncSurface (GST_VAAPI_DISPLAY_VADISPLAY (display),
      GST_VAAPI_OBJECT_ID (surface));
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaSyncSurface()"))
    return FALSE;

  return TRUE;
}
static gboolean
gst_vaapi_subpicture_create (GstVaapiSubpicture * subpicture,
    GstVaapiImage * image)
{
  GstVaapiDisplay *const display = GST_VAAPI_OBJECT_DISPLAY (subpicture);
  VASubpictureID subpicture_id;
  VAStatus status;

  GST_VAAPI_DISPLAY_LOCK (display);
  status = vaCreateSubpicture (GST_VAAPI_DISPLAY_VADISPLAY (display),
      GST_VAAPI_OBJECT_ID (image), &subpicture_id);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaCreateSubpicture()"))
    return FALSE;

  GST_DEBUG ("subpicture %" GST_VAAPI_ID_FORMAT,
      GST_VAAPI_ID_ARGS (subpicture_id));
  GST_VAAPI_OBJECT_ID (subpicture) = subpicture_id;
  subpicture->image = gst_vaapi_object_ref (image);
  return TRUE;
}
Example #25
0
static gboolean
gst_vaapi_surface_create(GstVaapiSurface *surface)
{
    GstVaapiDisplay * const display = GST_VAAPI_OBJECT_DISPLAY(surface);
    GstVaapiSurfacePrivate * const priv = surface->priv;
    VASurfaceID surface_id;
    VAStatus status;
    guint format;

    switch (priv->chroma_type) {
    case GST_VAAPI_CHROMA_TYPE_YUV420:
        format = VA_RT_FORMAT_YUV420;
        break;
    case GST_VAAPI_CHROMA_TYPE_YUV422:
        format = VA_RT_FORMAT_YUV422;
        break;
    case GST_VAAPI_CHROMA_TYPE_YUV444:
        format = VA_RT_FORMAT_YUV444;
        break;
    default:
        GST_DEBUG("unsupported chroma-type %u\n", priv->chroma_type);
        return FALSE;
    }

    GST_VAAPI_DISPLAY_LOCK(display);
    status = vaCreateSurfaces(
        GST_VAAPI_DISPLAY_VADISPLAY(display),
        priv->width,
        priv->height,
        format,
        1, &surface_id
    );
    GST_VAAPI_DISPLAY_UNLOCK(display);
    if (!vaapi_check_status(status, "vaCreateSurfaces()"))
        return FALSE;

    GST_DEBUG("surface %" GST_VAAPI_ID_FORMAT, GST_VAAPI_ID_ARGS(surface_id));
    GST_VAAPI_OBJECT_ID(surface) = surface_id;
    return TRUE;
}
Example #26
0
static void
gst_vaapi_image_destroy(GstVaapiImage *image)
{
    GstVaapiDisplay * const display = GST_VAAPI_OBJECT_DISPLAY(image);
    VAImageID image_id;
    VAStatus status;

    _gst_vaapi_image_unmap(image);

    image_id = GST_VAAPI_OBJECT_ID(image);
    GST_DEBUG("image %" GST_VAAPI_ID_FORMAT, GST_VAAPI_ID_ARGS(image_id));

    if (image_id != VA_INVALID_ID) {
        GST_VAAPI_DISPLAY_LOCK(display);
        status = vaDestroyImage(GST_VAAPI_DISPLAY_VADISPLAY(display), image_id);
        GST_VAAPI_DISPLAY_UNLOCK(display);
        if (!vaapi_check_status(status, "vaDestroyImage()"))
            g_warning("failed to destroy image %" GST_VAAPI_ID_FORMAT,
                      GST_VAAPI_ID_ARGS(image_id));
        GST_VAAPI_OBJECT_ID(image) = VA_INVALID_ID;
    }
}
Example #27
0
static int bind_image(VAImage *va_image, Image *image)
{
    VAAPIContext * const vaapi = vaapi_get_context();
    VAImageFormat * const va_format = &va_image->format;
    VAStatus status;
    void *va_image_data;
    unsigned int i;

    if (va_image->num_planes > MAX_IMAGE_PLANES)
        return -1;

    status = vaMapBuffer(vaapi->display, va_image->buf, &va_image_data);
    if (!vaapi_check_status(status, "vaMapBuffer()"))
        return -1;

    memset(image, 0, sizeof(*image));
    image->format = va_format->fourcc;
    if (is_vaapi_rgb_format(va_format)) {
        image->format = image_rgba_format(
            va_format->bits_per_pixel,
            va_format->byte_order == VA_MSB_FIRST,
            va_format->red_mask,
            va_format->green_mask,
            va_format->blue_mask,
            va_format->alpha_mask
        );
        if (!image->format)
            return -1;
    }

    image->width      = va_image->width;
    image->height     = va_image->height;
    image->num_planes = va_image->num_planes;
    for (i = 0; i < va_image->num_planes; i++) {
        image->pixels[i]  = (uint8_t *)va_image_data + va_image->offsets[i];
        image->pitches[i] = va_image->pitches[i];
    }
    return 0;
}
Example #28
0
static int
get_image_format(
    VAAPIContext   *vaapi,
    uint32_t        fourcc,
    VAImageFormat **image_format
)
{
    VAStatus status;
    int i;

    if (image_format)
        *image_format = NULL;

    if (!vaapi->image_formats || vaapi->n_image_formats == 0) {
        vaapi->image_formats = calloc(vaMaxNumImageFormats(vaapi->display),
                                      sizeof(vaapi->image_formats[0]));
        if (!vaapi->image_formats)
            return 0;

        status = vaQueryImageFormats(vaapi->display,
                                     vaapi->image_formats,
                                     &vaapi->n_image_formats);
        if (!vaapi_check_status(status, "vaQueryImageFormats()"))
            return 0;

        D(bug("%d image formats\n", vaapi->n_image_formats));
        for (i = 0; i < vaapi->n_image_formats; i++)
            D(bug("  %s\n", string_of_VAImageFormat(&vaapi->image_formats[i])));
    }

    for (i = 0; i < vaapi->n_image_formats; i++) {
        if (vaapi->image_formats[i].fourcc == fourcc) {
            if (image_format)
                *image_format = &vaapi->image_formats[i];
            return 1;
        }
    }
    return 0;
}
/**
 * gst_vaapi_get_config_attribute:
 * @display: a #GstVaapiDisplay
 * @profile: a VA profile
 * @entrypoint: a VA entrypoint
 * @type: a VA config attribute type
 * @out_value_ptr: return location for the config attribute value
 *
 * Determines the value for the VA config attribute @type and the
 * given @profile/@entrypoint pair. If @out_value_ptr is %NULL, then
 * this functions acts as a way to query whether the underlying VA
 * driver supports the specified attribute @type, no matter the
 * returned value.
 *
 * Note: this function only returns success if the VA driver does
 * actually know about this config attribute type and that it returned
 * a valid value for it.
 *
 * Return value: %TRUE if the VA driver knows about the requested
 *   config attribute and returned a valid value, %FALSE otherwise
 */
gboolean
gst_vaapi_get_config_attribute (GstVaapiDisplay * display, VAProfile profile,
    VAEntrypoint entrypoint, VAConfigAttribType type, guint * out_value_ptr)
{
  VAConfigAttrib attrib;
  VAStatus status;

  g_return_val_if_fail (display != NULL, FALSE);

  GST_VAAPI_DISPLAY_LOCK (display);
  attrib.type = type;
  status = vaGetConfigAttributes (GST_VAAPI_DISPLAY_VADISPLAY (display),
      profile, entrypoint, &attrib, 1);
  GST_VAAPI_DISPLAY_UNLOCK (display);
  if (!vaapi_check_status (status, "vaGetConfigAttributes()"))
    return FALSE;
  if (attrib.value == VA_ATTRIB_NOT_SUPPORTED)
    return FALSE;

  if (out_value_ptr)
    *out_value_ptr = attrib.value;
  return TRUE;
}
Example #30
0
VaapiSurfaceGLXImpl::~VaapiSurfaceGLXImpl()
{
    // GNASH_REPORT_FUNCTION;

    log_debug(_("VaapiSurface::~VaapiSurface(): surface %p\n", surface()));

    if (!surface()) {
        return;
    }

    VaapiGlobalContext * gvactx = VaapiGlobalContext::get();
    if (!gvactx) {
        return;
    }

    VAStatus status;
    status = vaDestroySurfaceGLX(gvactx->display(), surface());
    if (!vaapi_check_status(status, "vaDestroySurfaceGLX()")) {
        return;
    }

    reset(0);
}