[Mesa-dev] [PATCH 2/2] implement NV_vdpau_interop v3

Christian König deathsimple at vodafone.de
Sun Oct 20 11:57:08 CEST 2013


Hi Marek,

I've just send out a v6 of the patch, please take a second look. Most 
things are fixed now, but there are still a couple of open issues:

> 3) There should also probably be some checking for
> GL_ARB_texture_non_power_of_two, but the spec doesn't say what we
> should do (probably return GL_INVALID_OPERATION).

Actually I thing VDPAU hold the answer to this. The specification there 
states that the different surfaces creation function should round up the 
width/height to supported values (which can then be queried later by the 
application). So we always will end up with correct values independent 
of GL_ARB_texture_non_power_of_two.

> 6) Registered and mapped VDPAU textures are not allowed to be
> re-specified by TexImage, TexSubImage, TexImage*Multisample,
> CopyTexImage, CopyTexSubImage, TexStorage, TexStorage*Multisample, and
> similar functions. This should be properly handled in those functions
> and GL errors should be returned.

I would rather like to avoid touching those functions, cause they are 
not directly related to the spec and I don't want to risk breaking 
anything there.

Would it valid so set/clear the immutable flag instead (honestly I don't 
have the slightest idea how the frontend handling works in this code)?

> 7) The extension spec says that all VDPAU textures should be
> y-inverted. Is that actually the case here?

Uhm, no idea? It does seems to work, but where is that information stored?

> 8) Do we actually have enough tests, so that we can say this feature 
> works?

Nope, somebody still needs to write piglit tests.

Christian.

Am 21.09.2013 19:18, schrieb Christian König:
> Exactly as I though.
>
> It's code that I never worked with and I only implemented it so far 
> that XBMC does indeed work, but clearly following the spec is 
> something different.
>
> I've committed the rest of the patchset, but I have my doubts that Tim 
> wants me to spend any more time on it, so we have a slightly resource 
> conflict here.
>
> So does anybody from the list want to volunteer to fix the things 
> Marek pointed out? Otherwise we should just leave it like this for now 
> and if nobody else volunteered till Wednesday we are trying to shift 
> priorities internally a bit.
>
> Thanks for the review,
> Christian.
>
> Am 21.09.2013 16:56, schrieb Marek Olšák:
>> 1) The Errors section of the spec isn't implemented properly.
>>
>> 2) Passing GL_TEXTURE_RECTANGLE to the new functions should generate
>> an error if ctx->Extensions.NV_texture_rectangle is false.
>>
>> 3) There should also probably be some checking for
>> GL_ARB_texture_non_power_of_two, but the spec doesn't say what we
>> should do (probably return GL_INVALID_OPERATION).
>>
>> 4) VDPAUGetSurfaceivNV isn't implemented properly.
>>
>> 5) The unregistering in VDPAUFiniNV should be implemented too.
>>
>> 6) Registered and mapped VDPAU textures are not allowed to be
>> re-specified by TexImage, TexSubImage, TexImage*Multisample,
>> CopyTexImage, CopyTexSubImage, TexStorage, TexStorage*Multisample, and
>> similar functions. This should be properly handled in those functions
>> and GL errors should be returned.
>>
>> 7) The extension spec says that all VDPAU textures should be
>> y-inverted. Is that actually the case here?
>>
>> 8) Do we actually have enough tests, so that we can say this feature 
>> works?
>>
>> Marek
>>
>> On Sat, Sep 21, 2013 at 12:32 PM, Christian König
>> <deathsimple at vodafone.de> wrote:
>>> From: Christian König <christian.koenig at amd.com>
>>>
>>> v2: Actually implement interop between the gallium
>>>      state tracker and the VDPAU backend.
>>>
>>> v3: Make it also available in non legacy contexts,
>>>      fix video buffer sharing.
>>>
>>> Signed-off-by: Christian König <christian.koenig at amd.com>
>>> ---
>>>   src/gallium/include/state_tracker/vdpau_interop.h |  49 ++++
>>>   src/gallium/state_trackers/vdpau/ftab.c           |  31 ++-
>>>   src/gallium/state_trackers/vdpau/output.c         |  11 +
>>>   src/gallium/state_trackers/vdpau/surface.c        |  21 ++
>>>   src/gallium/state_trackers/vdpau/vdpau_private.h  |   6 +
>>>   src/mapi/glapi/gen/Makefile.am                    |   1 +
>>>   src/mapi/glapi/gen/NV_vdpau_interop.xml           |  69 ++++++
>>>   src/mapi/glapi/gen/gl_API.xml                     |   2 +
>>>   src/mapi/glapi/gen/gl_genexec.py                  |   1 +
>>>   src/mesa/Makefile.sources                         |   4 +-
>>>   src/mesa/main/dd.h                                |  14 ++
>>>   src/mesa/main/extensions.c                        |   1 +
>>>   src/mesa/main/mtypes.h                            |   9 +
>>>   src/mesa/main/vdpau.c                             | 279 
>>> ++++++++++++++++++++++
>>>   src/mesa/main/vdpau.h                             |  72 ++++++
>>>   src/mesa/state_tracker/st_context.c               |   3 +
>>>   src/mesa/state_tracker/st_extensions.c            |   1 +
>>>   src/mesa/state_tracker/st_vdpau.c                 | 193 
>>> +++++++++++++++
>>>   src/mesa/state_tracker/st_vdpau.h                 |  42 ++++
>>>   19 files changed, 800 insertions(+), 9 deletions(-)
>>>   create mode 100644 src/gallium/include/state_tracker/vdpau_interop.h
>>>   create mode 100644 src/mapi/glapi/gen/NV_vdpau_interop.xml
>>>   create mode 100644 src/mesa/main/vdpau.c
>>>   create mode 100644 src/mesa/main/vdpau.h
>>>   create mode 100644 src/mesa/state_tracker/st_vdpau.c
>>>   create mode 100644 src/mesa/state_tracker/st_vdpau.h
>>>
>>> diff --git a/src/gallium/include/state_tracker/vdpau_interop.h 
>>> b/src/gallium/include/state_tracker/vdpau_interop.h
>>> new file mode 100644
>>> index 0000000..3ca7c9d
>>> --- /dev/null
>>> +++ b/src/gallium/include/state_tracker/vdpau_interop.h
>>> @@ -0,0 +1,49 @@
>>> +/************************************************************************** 
>>>
>>> + *
>>> + * Copyright 2013 Advanced Micro Devices, Inc.
>>> + * All Rights Reserved.
>>> + *
>>> + * Permission is hereby granted, free of charge, to any person 
>>> obtaining a
>>> + * copy of this software and associated documentation files (the
>>> + * "Software"), to deal in the Software without restriction, including
>>> + * without limitation the rights to use, copy, modify, merge, publish,
>>> + * distribute, sub license, and/or sell copies of the Software, and to
>>> + * permit persons to whom the Software is furnished to do so, 
>>> subject to
>>> + * the following conditions:
>>> + *
>>> + * The above copyright notice and this permission notice (including 
>>> the
>>> + * next paragraph) shall be included in all copies or substantial 
>>> portions
>>> + * of the Software.
>>> + *
>>> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 
>>> EXPRESS
>>> + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
>>> + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 
>>> NON-INFRINGEMENT.
>>> + * IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE 
>>> FOR
>>> + * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF 
>>> CONTRACT,
>>> + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
>>> + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
>>> + *
>>> + 
>>> **************************************************************************/
>>> +
>>> +/*
>>> + * Authors:
>>> + *      Christian König <christian.koenig at amd.com>
>>> + *
>>> + */
>>> +
>>> +#ifndef _VDPAU_INTEROP_H_
>>> +#define _VDPAU_INTEROP_H_
>>> +
>>> +/* driver specific functions for NV_vdpau_interop */
>>> +
>>> +#define VDP_FUNC_ID_BASE_DRIVER 0x2000
>>> +#define VDP_FUNC_ID_VIDEO_SURFACE_GALLIUM (VDP_FUNC_ID_BASE_DRIVER 
>>> + 0)
>>> +#define VDP_FUNC_ID_OUTPUT_SURFACE_GALLIUM (VDP_FUNC_ID_BASE_DRIVER 
>>> + 1)
>>> +
>>> +struct pipe_resource;
>>> +struct pipe_video_buffer;
>>> +
>>> +typedef struct pipe_video_buffer *VdpVideoSurfaceGallium(uint32_t 
>>> surface);
>>> +typedef struct pipe_resource *VdpOutputSurfaceGallium(uint32_t 
>>> surface);
>>> +
>>> +#endif /* _VDPAU_INTEROP_H_ */
>>> diff --git a/src/gallium/state_trackers/vdpau/ftab.c 
>>> b/src/gallium/state_trackers/vdpau/ftab.c
>>> index 81d16ec..2c84554 100644
>>> --- a/src/gallium/state_trackers/vdpau/ftab.c
>>> +++ b/src/gallium/state_trackers/vdpau/ftab.c
>>> @@ -26,6 +26,9 @@
>>> **************************************************************************/
>>>
>>>   #include <assert.h>
>>> +
>>> +#include "util/u_memory.h"
>>> +
>>>   #include "vdpau_private.h"
>>>
>>>   static void* ftab[67] =
>>> @@ -104,19 +107,31 @@ static void* ftab_winsys[1] =
>>>      &vlVdpPresentationQueueTargetCreateX11  /* 
>>> VDP_FUNC_ID_PRESENTATION_QUEUE_TARGET_CREATE_X11 */
>>>   };
>>>
>>> +static void* ftab_driver[2] =
>>> +{
>>> +   &vlVdpVideoSurfaceGallium, /* VDP_FUNC_ID_SURFACE_GALLIUM */
>>> +   &vlVdpOutputSurfaceGallium /* VDP_FUNC_ID_OUTPUT_SURFACE_GALLIUM */
>>> +};
>>> +
>>>   boolean vlGetFuncFTAB(VdpFuncId function_id, void **func)
>>>   {
>>>      assert(func);
>>> +   *func = NULL;
>>> +
>>>      if (function_id < VDP_FUNC_ID_BASE_WINSYS) {
>>> -      if (function_id > 66)
>>> -         return FALSE;
>>> -      *func = ftab[function_id];
>>> -   }
>>> -   else {
>>> +      if (function_id < Elements(ftab))
>>> +         *func = ftab[function_id];
>>> +
>>> +   } else if (function_id < VDP_FUNC_ID_BASE_DRIVER) {
>>>         function_id -= VDP_FUNC_ID_BASE_WINSYS;
>>> -      if (function_id > 0)
>>> -         return FALSE;
>>> -      *func = ftab_winsys[function_id];
>>> +      if (function_id < Elements(ftab_winsys))
>>> +         *func = ftab_winsys[function_id];
>>> +
>>> +   } else {
>>> +      function_id -= VDP_FUNC_ID_BASE_DRIVER;
>>> +      if (function_id < Elements(ftab_driver))
>>> +         *func = ftab_driver[function_id];
>>>      }
>>> +
>>>      return *func != NULL;
>>>   }
>>> diff --git a/src/gallium/state_trackers/vdpau/output.c 
>>> b/src/gallium/state_trackers/vdpau/output.c
>>> index 7266cdb..35da715 100644
>>> --- a/src/gallium/state_trackers/vdpau/output.c
>>> +++ b/src/gallium/state_trackers/vdpau/output.c
>>> @@ -724,3 +724,14 @@ 
>>> vlVdpOutputSurfaceRenderBitmapSurface(VdpOutputSurface 
>>> destination_surface,
>>>
>>>      return VDP_STATUS_OK;
>>>   }
>>> +
>>> +struct pipe_resource *vlVdpOutputSurfaceGallium(VdpOutputSurface 
>>> surface)
>>> +{
>>> +   vlVdpOutputSurface *vlsurface;
>>> +
>>> +   vlsurface = vlGetDataHTAB(surface);
>>> +   if (!vlsurface || !vlsurface->surface)
>>> +      return NULL;
>>> +
>>> +   return vlsurface->surface->texture;
>>> +}
>>> diff --git a/src/gallium/state_trackers/vdpau/surface.c 
>>> b/src/gallium/state_trackers/vdpau/surface.c
>>> index 8e39d68..dd434aa 100644
>>> --- a/src/gallium/state_trackers/vdpau/surface.c
>>> +++ b/src/gallium/state_trackers/vdpau/surface.c
>>> @@ -359,3 +359,24 @@ vlVdpVideoSurfaceClear(vlVdpSurface *vlsurf)
>>>      }
>>>      pipe->flush(pipe, NULL, 0);
>>>   }
>>> +
>>> +/**
>>> + * Interop to mesa state tracker
>>> + */
>>> +struct pipe_video_buffer *vlVdpVideoSurfaceGallium(VdpVideoSurface 
>>> surface)
>>> +{
>>> +   vlVdpSurface *p_surf = vlGetDataHTAB(surface);
>>> +   if (!p_surf)
>>> +      return NULL;
>>> +
>>> +   pipe_mutex_lock(p_surf->device->mutex);
>>> +   if (p_surf->video_buffer == NULL) {
>>> +      struct pipe_context *pipe = p_surf->device->context;
>>> +
>>> +      /* try to create a video buffer if we don't already have one */
>>> +      p_surf->video_buffer = pipe->create_video_buffer(pipe, 
>>> &p_surf->templat);
>>> +   }
>>> +   pipe_mutex_unlock(p_surf->device->mutex);
>>> +
>>> +   return p_surf->video_buffer;
>>> +}
>>> diff --git a/src/gallium/state_trackers/vdpau/vdpau_private.h 
>>> b/src/gallium/state_trackers/vdpau/vdpau_private.h
>>> index 54545fe..fe3bc3e 100644
>>> --- a/src/gallium/state_trackers/vdpau/vdpau_private.h
>>> +++ b/src/gallium/state_trackers/vdpau/vdpau_private.h
>>> @@ -36,6 +36,8 @@
>>>   #include "pipe/p_compiler.h"
>>>   #include "pipe/p_video_codec.h"
>>>
>>> +#include "state_tracker/vdpau_interop.h"
>>> +
>>>   #include "util/u_debug.h"
>>>   #include "util/u_rect.h"
>>>   #include "os/os_thread.h"
>>> @@ -474,6 +476,10 @@ VdpVideoMixerGetAttributeValues 
>>> vlVdpVideoMixerGetAttributeValues;
>>>   VdpVideoMixerDestroy vlVdpVideoMixerDestroy;
>>>   VdpGenerateCSCMatrix vlVdpGenerateCSCMatrix;
>>>
>>> +/* interop to mesa state tracker */
>>> +VdpVideoSurfaceGallium vlVdpVideoSurfaceGallium;
>>> +VdpOutputSurfaceGallium vlVdpOutputSurfaceGallium;
>>> +
>>>   #define VDPAU_OUT   0
>>>   #define VDPAU_ERR   1
>>>   #define VDPAU_WARN  2
>>> diff --git a/src/mapi/glapi/gen/Makefile.am 
>>> b/src/mapi/glapi/gen/Makefile.am
>>> index d4fbd35..bd82e54 100644
>>> --- a/src/mapi/glapi/gen/Makefile.am
>>> +++ b/src/mapi/glapi/gen/Makefile.am
>>> @@ -131,6 +131,7 @@ API_XML = \
>>>          NV_conditional_render.xml \
>>>          NV_primitive_restart.xml \
>>>          NV_texture_barrier.xml \
>>> +       NV_vdpau_interop.xml \
>>>          OES_EGL_image.xml \
>>>          GL3x.xml
>>>
>>> diff --git a/src/mapi/glapi/gen/NV_vdpau_interop.xml 
>>> b/src/mapi/glapi/gen/NV_vdpau_interop.xml
>>> new file mode 100644
>>> index 0000000..cf5f0ed
>>> --- /dev/null
>>> +++ b/src/mapi/glapi/gen/NV_vdpau_interop.xml
>>> @@ -0,0 +1,69 @@
>>> +<?xml version="1.0"?>
>>> +<!DOCTYPE OpenGLAPI SYSTEM "gl_API.dtd">
>>> +
>>> +<OpenGLAPI>
>>> +
>>> +<category name="GL_NV_vdpau_interop" number="396">
>>> +
>>> +    <function name="VDPAUInitNV" offset="assign">
>>> +       <param name="vdpDevice" type="const GLvoid *"/>
>>> +       <param name="getProcAddress" type="const GLvoid *"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUFiniNV" offset="assign"/>
>>> +
>>> +    <function name="VDPAURegisterVideoSurfaceNV" offset="assign">
>>> +        <return type="GLintptr"/>
>>> +       <param name="vdpSurface" type="const GLvoid *"/>
>>> +       <param name="target" type="GLenum"/>
>>> +       <param name="numTextureNames" type="GLsizei"/>
>>> +       <param name="textureNames" type="const GLuint *"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAURegisterOutputSurfaceNV" offset="assign">
>>> +        <return type="GLintptr"/>
>>> +       <param name="vdpSurface" type="const GLvoid *"/>
>>> +       <param name="target" type="GLenum"/>
>>> +       <param name="numTextureNames" type="GLsizei"/>
>>> +       <param name="textureNames" type="const GLuint *"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUIsSurfaceNV" offset="assign">
>>> +       <param name="surface" type="GLintptr"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUUnregisterSurfaceNV" offset="assign">
>>> +       <param name="surface" type="GLintptr"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUGetSurfaceivNV" offset="assign">
>>> +       <param name="surface" type="GLintptr"/>
>>> +       <param name="pname" type="GLenum"/>
>>> +       <param name="bufSize" type="GLsizei"/>
>>> +       <param name="length" type="GLsizei *"/>
>>> +       <param name="values" type="GLint *"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUSurfaceAccessNV" offset="assign">
>>> +       <param name="surface" type="GLintptr"/>
>>> +       <param name="access" type="GLenum"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUMapSurfacesNV" offset="assign">
>>> +       <param name="numSurfaces" type="GLsizei"/>
>>> +       <param name="surfaces" type="const GLintptr *"/>
>>> +    </function>
>>> +
>>> +    <function name="VDPAUUnmapSurfacesNV" offset="assign">
>>> +       <param name="numSurfaces" type="GLsizei"/>
>>> +       <param name="surfaces" type="const GLintptr *"/>
>>> +    </function>
>>> +
>>> +    <enum name="SURFACE_STATE_NV"      value="0x86EB"/>
>>> +    <enum name="SURFACE_REGISTERED_NV" value="0x86FD"/>
>>> +    <enum name="SURFACE_MAPPED_NV"     value="0x8700"/>
>>> +    <enum name="WRITE_DISCARD_NV"      value="0x88BE"/>
>>> +
>>> +</category>
>>> +
>>> +</OpenGLAPI>
>>> diff --git a/src/mapi/glapi/gen/gl_API.xml 
>>> b/src/mapi/glapi/gen/gl_API.xml
>>> index 71aa9a7..5700caa 100644
>>> --- a/src/mapi/glapi/gen/gl_API.xml
>>> +++ b/src/mapi/glapi/gen/gl_API.xml
>>> @@ -13148,4 +13148,6 @@
>>>
>>>   <xi:include href="EXT_transform_feedback.xml" 
>>> xmlns:xi="http://www.w3.org/2001/XInclude"/>
>>>
>>> +<xi:include href="NV_vdpau_interop.xml" 
>>> xmlns:xi="http://www.w3.org/2001/XInclude"/>
>>> +
>>>   </OpenGLAPI>
>>> diff --git a/src/mapi/glapi/gen/gl_genexec.py 
>>> b/src/mapi/glapi/gen/gl_genexec.py
>>> index be82f90..d76c7ae 100644
>>> --- a/src/mapi/glapi/gen/gl_genexec.py
>>> +++ b/src/mapi/glapi/gen/gl_genexec.py
>>> @@ -110,6 +110,7 @@ header = """/**
>>>   #include "main/syncobj.h"
>>>   #include "main/formatquery.h"
>>>   #include "main/dispatch.h"
>>> +#include "main/vdpau.h"
>>>   #include "vbo/vbo.h"
>>>
>>>
>>> diff --git a/src/mesa/Makefile.sources b/src/mesa/Makefile.sources
>>> index 122ea8e..85b4fe1 100644
>>> --- a/src/mesa/Makefile.sources
>>> +++ b/src/mesa/Makefile.sources
>>> @@ -107,6 +107,7 @@ MAIN_FILES = \
>>>          $(SRCDIR)main/uniforms.c \
>>>          $(SRCDIR)main/uniform_query.cpp \
>>>          $(SRCDIR)main/varray.c \
>>> +       $(SRCDIR)main/vdpau.c \
>>>          $(SRCDIR)main/version.c \
>>>          $(SRCDIR)main/viewport.c \
>>>          $(SRCDIR)main/vtxfmt.c \
>>> @@ -247,7 +248,8 @@ STATETRACKER_FILES = \
>>>          $(SRCDIR)state_tracker/st_manager.c \
>>>          $(SRCDIR)state_tracker/st_mesa_to_tgsi.c \
>>>          $(SRCDIR)state_tracker/st_program.c \
>>> -       $(SRCDIR)state_tracker/st_texture.c
>>> +       $(SRCDIR)state_tracker/st_texture.c \
>>> +       $(SRCDIR)state_tracker/st_vdpau.c
>>>
>>>   PROGRAM_FILES = \
>>>          $(SRCDIR)program/arbprogparse.c \
>>> diff --git a/src/mesa/main/dd.h b/src/mesa/main/dd.h
>>> index c1d9b2c..a3ee0b7 100644
>>> --- a/src/mesa/main/dd.h
>>> +++ b/src/mesa/main/dd.h
>>> @@ -843,6 +843,20 @@ struct dd_function_table {
>>>                                struct gl_framebuffer *fb,
>>>                                GLuint index,
>>>                                GLfloat *outValue);
>>> +
>>> +   /**
>>> +    * \name NV_vdpau_interop interface
>>> +    */
>>> +   void (*VDPAUMapSurface)(struct gl_context *ctx, GLenum target,
>>> +                           GLenum access, GLboolean output,
>>> +                           struct gl_texture_object *texObj,
>>> +                           struct gl_texture_image *texImage,
>>> +                           const GLvoid *vdpSurface, GLuint index);
>>> +   void (*VDPAUUnmapSurface)(struct gl_context *ctx, GLenum target,
>>> +                             GLenum access, GLboolean output,
>>> +                             struct gl_texture_object *texObj,
>>> +                             struct gl_texture_image *texImage,
>>> +                             const GLvoid *vdpSurface, GLuint index);
>>>   };
>>>
>>>
>>> diff --git a/src/mesa/main/extensions.c b/src/mesa/main/extensions.c
>>> index 34615e3..a735e93 100644
>>> --- a/src/mesa/main/extensions.c
>>> +++ b/src/mesa/main/extensions.c
>>> @@ -332,6 +332,7 @@ static const struct extension extension_table[] = {
>>>      { "GL_NV_texture_barrier", 
>>> o(NV_texture_barrier),                      GL, 2009 },
>>>      { "GL_NV_texture_env_combine4", 
>>> o(NV_texture_env_combine4),                 GLL, 1999 },
>>>      { "GL_NV_texture_rectangle", 
>>> o(NV_texture_rectangle),                    GLL, 2000 },
>>> +   { "GL_NV_vdpau_interop", 
>>> o(NV_vdpau_interop),                        GL, 2010 },
>>>      { "GL_S3_s3tc", o(ANGLE_texture_compression_dxt),           GL, 
>>> 1999 },
>>>      { "GL_SGIS_generate_mipmap", 
>>> o(dummy_true),                              GLL, 1997 },
>>>      { "GL_SGIS_texture_border_clamp", 
>>> o(ARB_texture_border_clamp),                GLL, 1997 },
>>> diff --git a/src/mesa/main/mtypes.h b/src/mesa/main/mtypes.h
>>> index c88c1c6..40346e4 100644
>>> --- a/src/mesa/main/mtypes.h
>>> +++ b/src/mesa/main/mtypes.h
>>> @@ -3196,6 +3196,7 @@ struct gl_extensions
>>>      GLboolean NV_texture_barrier;
>>>      GLboolean NV_texture_env_combine4;
>>>      GLboolean NV_texture_rectangle;
>>> +   GLboolean NV_vdpau_interop;
>>>      GLboolean TDFX_texture_compression_FXT1;
>>>      GLboolean OES_EGL_image;
>>>      GLboolean OES_draw_texture;
>>> @@ -3726,6 +3727,14 @@ struct gl_context
>>>      struct st_context *st;
>>>      void *aelt_context;
>>>      /*@}*/
>>> +
>>> +   /**
>>> +    * \name NV_vdpau_interop
>>> +    */
>>> +   /*@{*/
>>> +   const void *vdpDevice;
>>> +   const void *vdpGetProcAddress;
>>> +   /*@}*/
>>>   };
>>>
>>>
>>> diff --git a/src/mesa/main/vdpau.c b/src/mesa/main/vdpau.c
>>> new file mode 100644
>>> index 0000000..68f087b
>>> --- /dev/null
>>> +++ b/src/mesa/main/vdpau.c
>>> @@ -0,0 +1,279 @@
>>> +/************************************************************************** 
>>>
>>> + *
>>> + * Copyright 2013 Advanced Micro Devices, Inc.
>>> + * All Rights Reserved.
>>> + *
>>> + * Permission is hereby granted, free of charge, to any person 
>>> obtaining a
>>> + * copy of this software and associated documentation files (the
>>> + * "Software"), to deal in the Software without restriction, including
>>> + * without limitation the rights to use, copy, modify, merge, publish,
>>> + * distribute, sub license, and/or sell copies of the Software, and to
>>> + * permit persons to whom the Software is furnished to do so, 
>>> subject to
>>> + * the following conditions:
>>> + *
>>> + * The above copyright notice and this permission notice (including 
>>> the
>>> + * next paragraph) shall be included in all copies or substantial 
>>> portions
>>> + * of the Software.
>>> + *
>>> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 
>>> EXPRESS
>>> + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
>>> + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 
>>> NON-INFRINGEMENT.
>>> + * IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE 
>>> FOR
>>> + * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF 
>>> CONTRACT,
>>> + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
>>> + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
>>> + *
>>> + 
>>> **************************************************************************/
>>> +
>>> +/*
>>> + * Authors:
>>> + *      Christian König <christian.koenig at amd.com>
>>> + *
>>> + */
>>> +
>>> +#include <stdbool.h>
>>> +#include "context.h"
>>> +#include "glformats.h"
>>> +#include "texobj.h"
>>> +#include "teximage.h"
>>> +#include "vdpau.h"
>>> +
>>> +#define MAX_TEXTURES 4
>>> +
>>> +struct vdp_surface
>>> +{
>>> +   GLenum target;
>>> +   struct gl_texture_object *textures[MAX_TEXTURES];
>>> +   GLenum access;
>>> +   GLboolean output;
>>> +   const GLvoid *vdpSurface;
>>> +};
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUInitNV(const GLvoid *vdpDevice, const GLvoid 
>>> *getProcAddress)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (!vdpDevice) {
>>> +      _mesa_error(ctx, GL_INVALID_VALUE, "vdpDevice");
>>> +      return;
>>> +   }
>>> +
>>> +   if (!getProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_VALUE, "getProcAddress");
>>> +      return;
>>> +   }
>>> +
>>> +   if (ctx->vdpDevice || ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUInitNV");
>>> +      return;
>>> +   }
>>> +
>>> +   ctx->vdpDevice = vdpDevice;
>>> +   ctx->vdpGetProcAddress = getProcAddress;
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUFiniNV()
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUFiniNV");
>>> +      return;
>>> +   }
>>> +
>>> +   /* TODO: unregister all surfaces */
>>> +
>>> +   ctx->vdpDevice = 0;
>>> +   ctx->vdpGetProcAddress = 0;
>>> +}
>>> +
>>> +static GLintptr
>>> +register_surface(struct gl_context *ctx, GLboolean isOutput,
>>> +                 const GLvoid *vdpSurface, GLenum target,
>>> +                 GLsizei numTextureNames, const GLuint *textureNames)
>>> +{
>>> +   struct vdp_surface *surf;
>>> +   int i;
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, 
>>> "VDPAURegisterSurfaceNV");
>>> +      return (GLintptr)NULL;
>>> +   }
>>> +
>>> +   if (target != GL_TEXTURE_2D && target != GL_TEXTURE_RECTANGLE) {
>>> +      _mesa_error(ctx, GL_INVALID_ENUM, "VDPAURegisterSurfaceNV");
>>> +      return (GLintptr)NULL;
>>> +   }
>>> +
>>> +   surf = MALLOC_STRUCT( vdp_surface );
>>> +   surf->vdpSurface = vdpSurface;
>>> +   surf->target = target;
>>> +   surf->access = GL_READ_WRITE;
>>> +   surf->output = isOutput;
>>> +   for (i = 0; i < numTextureNames; ++i) {
>>> +      struct gl_texture_object *tex;
>>> +      tex  = _mesa_lookup_texture(ctx, textureNames[i]);
>>> +
>>> +      if (tex->Target == 0)
>>> +         tex->Target = target;
>>> +      else if (tex->Target != target) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION,
>>> +                     "VDPAURegisterSurfaceNV(target mismatch)");
>>> +         return (GLintptr)NULL;
>>> +      }
>>> +
>>> +      surf->textures[i] = tex;
>>> +   }
>>> +
>>> +   return (GLintptr)surf;
>>> +}
>>> +
>>> +GLintptr GLAPIENTRY
>>> +_mesa_VDPAURegisterVideoSurfaceNV(const GLvoid *vdpSurface, GLenum 
>>> target,
>>> +                                  GLsizei numTextureNames,
>>> +                                  const GLuint *textureNames)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (numTextureNames != 4) {
>>> +      _mesa_error(ctx, GL_INVALID_VALUE, 
>>> "VDPAURegisterVideoSurfaceNV");
>>> +      return (GLintptr)NULL;
>>> +   }
>>> +
>>> +   return register_surface(ctx, false, vdpSurface, target,
>>> +                           numTextureNames, textureNames);
>>> +}
>>> +
>>> +GLintptr GLAPIENTRY
>>> +_mesa_VDPAURegisterOutputSurfaceNV(const GLvoid *vdpSurface, GLenum 
>>> target,
>>> +                                   GLsizei numTextureNames,
>>> +                                   const GLuint *textureNames)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (numTextureNames != 1) {
>>> +      _mesa_error(ctx, GL_INVALID_VALUE, 
>>> "VDPAURegisterVideoSurfaceNV");
>>> +      return (GLintptr)NULL;
>>> +   }
>>> +
>>> +   return register_surface(ctx, true, vdpSurface, target,
>>> +                           numTextureNames, textureNames);
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUIsSurfaceNV(GLintptr surface)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUIsSurfaceNV");
>>> +      return;
>>> +   }
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUUnregisterSurfaceNV(GLintptr surface)
>>> +{
>>> +   FREE((struct vdp_surface *)surface);
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUGetSurfaceivNV(GLintptr surface, GLenum pname, GLsizei 
>>> bufSize,
>>> +                          GLsizei *length, GLint *values)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUGetSurfaceivNV");
>>> +      return;
>>> +   }
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUSurfaceAccessNV(GLintptr surface, GLenum access)
>>> +{
>>> +   struct vdp_surface *surf = (struct vdp_surface *)surface;
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUSurfaceAccessNV");
>>> +      return;
>>> +   }
>>> +
>>> +   surf->access = access;
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUMapSurfacesNV(GLsizei numSurfaces, const GLintptr 
>>> *surfaces)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +   int i, j;
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUUnmapSurfacesNV");
>>> +      return;
>>> +   }
>>> +
>>> +   for (i = 0; i < numSurfaces; ++i) {
>>> +      struct vdp_surface *surf = (struct vdp_surface *)surfaces[i];
>>> +      unsigned numTextureNames = surf->output ? 1 : 4;
>>> +
>>> +      for (j = 0; j < numTextureNames; ++j) {
>>> +         struct gl_texture_object *tex = surf->textures[j];
>>> +         struct gl_texture_image *image;
>>> +
>>> +         _mesa_lock_texture(ctx, tex);
>>> +         image = _mesa_get_tex_image(ctx, tex, surf->target, 0);
>>> +         if (!image) {
>>> +            _mesa_error(ctx, GL_OUT_OF_MEMORY, "VDPAUMapSurfacesNV");
>>> +            _mesa_unlock_texture(ctx, tex);
>>> +            return;
>>> +         }
>>> +
>>> +         ctx->Driver.FreeTextureImageBuffer(ctx, image);
>>> +
>>> +         ctx->Driver.VDPAUMapSurface(ctx, surf->target, surf->access,
>>> +                                     surf->output, tex, image,
>>> +                                     surf->vdpSurface, j);
>>> +
>>> +         _mesa_unlock_texture(ctx, tex);
>>> +      }
>>> +   }
>>> +}
>>> +
>>> +void GLAPIENTRY
>>> +_mesa_VDPAUUnmapSurfacesNV(GLsizei numSurfaces, const GLintptr 
>>> *surfaces)
>>> +{
>>> +   GET_CURRENT_CONTEXT(ctx);
>>> +   int i, j;
>>> +
>>> +   if (!ctx->vdpDevice || !ctx->vdpGetProcAddress) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUUnmapSurfacesNV");
>>> +      return;
>>> +   }
>>> +
>>> +   for (i = 0; i < numSurfaces; ++i) {
>>> +      struct vdp_surface *surf = (struct vdp_surface *)surfaces[i];
>>> +      unsigned numTextureNames = surf->output ? 1 : 4;
>>> +
>>> +      for (j = 0; j < numTextureNames; ++j) {
>>> +         struct gl_texture_object *tex = surf->textures[j];
>>> +         struct gl_texture_image *image;
>>> +
>>> +         _mesa_lock_texture(ctx, tex);
>>> +
>>> +         image = _mesa_select_tex_image(ctx, tex, surf->target, 0);
>>> +
>>> +         ctx->Driver.VDPAUUnmapSurface(ctx, surf->target, 
>>> surf->access,
>>> +                                       surf->output, tex, image,
>>> +                                       surf->vdpSurface, j);
>>> +
>>> +         if (image)
>>> +            ctx->Driver.FreeTextureImageBuffer(ctx, image);
>>> +
>>> +         _mesa_unlock_texture(ctx, tex);
>>> +      }
>>> +   }
>>> +}
>>> diff --git a/src/mesa/main/vdpau.h b/src/mesa/main/vdpau.h
>>> new file mode 100644
>>> index 0000000..f32d6da
>>> --- /dev/null
>>> +++ b/src/mesa/main/vdpau.h
>>> @@ -0,0 +1,72 @@
>>> +/************************************************************************** 
>>>
>>> + *
>>> + * Copyright 2013 Advanced Micro Devices, Inc.
>>> + * All Rights Reserved.
>>> + *
>>> + * Permission is hereby granted, free of charge, to any person 
>>> obtaining a
>>> + * copy of this software and associated documentation files (the
>>> + * "Software"), to deal in the Software without restriction, including
>>> + * without limitation the rights to use, copy, modify, merge, publish,
>>> + * distribute, sub license, and/or sell copies of the Software, and to
>>> + * permit persons to whom the Software is furnished to do so, 
>>> subject to
>>> + * the following conditions:
>>> + *
>>> + * The above copyright notice and this permission notice (including 
>>> the
>>> + * next paragraph) shall be included in all copies or substantial 
>>> portions
>>> + * of the Software.
>>> + *
>>> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 
>>> EXPRESS
>>> + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
>>> + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 
>>> NON-INFRINGEMENT.
>>> + * IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE 
>>> FOR
>>> + * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF 
>>> CONTRACT,
>>> + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
>>> + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
>>> + *
>>> + 
>>> **************************************************************************/
>>> +
>>> +/*
>>> + * Authors:
>>> + *      Christian König <christian.koenig at amd.com>
>>> + *
>>> + */
>>> +
>>> +#ifndef VDPAU_H
>>> +#define VDPAU_H
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUInitNV(const GLvoid *vdpDevice, const GLvoid 
>>> *getProcAddress);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUFiniNV(void);
>>> +
>>> +extern GLintptr GLAPIENTRY
>>> +_mesa_VDPAURegisterVideoSurfaceNV(const GLvoid *vdpSurface, GLenum 
>>> target,
>>> +                                  GLsizei numTextureNames,
>>> +                                  const GLuint *textureNames);
>>> +
>>> +extern GLintptr GLAPIENTRY
>>> +_mesa_VDPAURegisterOutputSurfaceNV(const GLvoid *vdpSurface, GLenum 
>>> target,
>>> +                                   GLsizei numTextureNames,
>>> +                                   const GLuint *textureNames);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUIsSurfaceNV(GLintptr surface);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUUnregisterSurfaceNV(GLintptr surface);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUGetSurfaceivNV(GLintptr surface, GLenum pname, GLsizei 
>>> bufSize,
>>> +                          GLsizei *length, GLint *values);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUSurfaceAccessNV(GLintptr surface, GLenum access);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUMapSurfacesNV(GLsizei numSurfaces, const GLintptr 
>>> *surfaces);
>>> +
>>> +extern void GLAPIENTRY
>>> +_mesa_VDPAUUnmapSurfacesNV(GLsizei numSurfaces, const GLintptr 
>>> *surfaces);
>>> +
>>> +#endif /* VDPAU_H */
>>> diff --git a/src/mesa/state_tracker/st_context.c 
>>> b/src/mesa/state_tracker/st_context.c
>>> index 80393cf..1194437 100644
>>> --- a/src/mesa/state_tracker/st_context.c
>>> +++ b/src/mesa/state_tracker/st_context.c
>>> @@ -65,6 +65,7 @@
>>>   #include "st_extensions.h"
>>>   #include "st_gen_mipmap.h"
>>>   #include "st_program.h"
>>> +#include "st_vdpau.h"
>>>   #include "pipe/p_context.h"
>>>   #include "util/u_inlines.h"
>>>   #include "util/u_upload_mgr.h"
>>> @@ -356,5 +357,7 @@ void st_init_driver_functions(struct 
>>> dd_function_table *functions)
>>>      st_init_xformfb_functions(functions);
>>>      st_init_syncobj_functions(functions);
>>>
>>> +   st_init_vdpau_functions(functions);
>>> +
>>>      functions->UpdateState = st_invalidate_state;
>>>   }
>>> diff --git a/src/mesa/state_tracker/st_extensions.c 
>>> b/src/mesa/state_tracker/st_extensions.c
>>> index 97dd732..2898a8d 100644
>>> --- a/src/mesa/state_tracker/st_extensions.c
>>> +++ b/src/mesa/state_tracker/st_extensions.c
>>> @@ -564,6 +564,7 @@ void st_init_extensions(struct st_context *st)
>>>      ctx->Extensions.NV_fog_distance = GL_TRUE;
>>>      ctx->Extensions.NV_texture_env_combine4 = GL_TRUE;
>>>      ctx->Extensions.NV_texture_rectangle = GL_TRUE;
>>> +   ctx->Extensions.NV_vdpau_interop = GL_TRUE;
>>>
>>>      ctx->Extensions.OES_EGL_image = GL_TRUE;
>>>      ctx->Extensions.OES_EGL_image_external = GL_TRUE;
>>> diff --git a/src/mesa/state_tracker/st_vdpau.c 
>>> b/src/mesa/state_tracker/st_vdpau.c
>>> new file mode 100644
>>> index 0000000..c6ca909
>>> --- /dev/null
>>> +++ b/src/mesa/state_tracker/st_vdpau.c
>>> @@ -0,0 +1,193 @@
>>> +/************************************************************************** 
>>>
>>> + *
>>> + * Copyright 2013 Advanced Micro Devices, Inc.
>>> + * All Rights Reserved.
>>> + *
>>> + * Permission is hereby granted, free of charge, to any person 
>>> obtaining a
>>> + * copy of this software and associated documentation files (the
>>> + * "Software"), to deal in the Software without restriction, including
>>> + * without limitation the rights to use, copy, modify, merge, publish,
>>> + * distribute, sub license, and/or sell copies of the Software, and to
>>> + * permit persons to whom the Software is furnished to do so, 
>>> subject to
>>> + * the following conditions:
>>> + *
>>> + * The above copyright notice and this permission notice (including 
>>> the
>>> + * next paragraph) shall be included in all copies or substantial 
>>> portions
>>> + * of the Software.
>>> + *
>>> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 
>>> EXPRESS
>>> + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
>>> + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 
>>> NON-INFRINGEMENT.
>>> + * IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE 
>>> FOR
>>> + * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF 
>>> CONTRACT,
>>> + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
>>> + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
>>> + *
>>> + 
>>> **************************************************************************/
>>> +
>>> +/*
>>> + * Authors:
>>> + *      Christian König <christian.koenig at amd.com>
>>> + *
>>> + */
>>> +
>>> +#include "main/texobj.h"
>>> +#include "main/teximage.h"
>>> +#include "main/errors.h"
>>> +#include "program/prog_instruction.h"
>>> +
>>> +#include "pipe/p_state.h"
>>> +#include "pipe/p_video_codec.h"
>>> +
>>> +#include "state_tracker/drm_driver.h"
>>> +#include "state_tracker/vdpau_interop.h"
>>> +
>>> +#include "util/u_inlines.h"
>>> +
>>> +#include "st_vdpau.h"
>>> +#include "st_context.h"
>>> +#include "st_texture.h"
>>> +#include "st_format.h"
>>> +
>>> +static void
>>> +st_vdpau_map_surface(struct gl_context *ctx, GLenum target, GLenum 
>>> access,
>>> +                     GLboolean output, struct gl_texture_object 
>>> *texObj,
>>> +                     struct gl_texture_image *texImage,
>>> +                     const GLvoid *vdpSurface, GLuint index)
>>> +{
>>> +   int (*getProcAddr)(uint32_t device, uint32_t id, void **ptr);
>>> +   uint32_t device = (uintptr_t)ctx->vdpDevice;
>>> +
>>> +   struct st_context *st = st_context(ctx);
>>> +   struct st_texture_object *stObj = st_texture_object(texObj);
>>> +   struct st_texture_image *stImage = st_texture_image(texImage);
>>> +
>>> +   struct pipe_resource *res;
>>> +   struct pipe_sampler_view *sv, templ;
>>> +   gl_format texFormat;
>>> +
>>> +   getProcAddr = ctx->vdpGetProcAddress;
>>> +   if (output) {
>>> +      VdpOutputSurfaceGallium *f;
>>> +
>>> +      if (getProcAddr(device, VDP_FUNC_ID_OUTPUT_SURFACE_GALLIUM, 
>>> (void**)&f)) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +         return;
>>> +      }
>>> +
>>> +      res = f((uintptr_t)vdpSurface);
>>> +
>>> +      if (!res) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +         return;
>>> +      }
>>> +
>>> +      /* do we have different screen objects ? */
>>> +      if (res->screen != st->pipe->screen) {
>>> +         struct winsys_handle handle;
>>> +
>>> +         /* export the resource from the other context */
>>> +         memset(&handle, 0, sizeof(handle));
>>> +         handle.type = DRM_API_HANDLE_TYPE_SHARED;
>>> + res->screen->resource_get_handle(res->screen, res, &handle);
>>> +
>>> +         /* and import it into this one */
>>> +         res = 
>>> st->pipe->screen->resource_from_handle(st->pipe->screen, res, &handle);
>>> +      }
>>> +
>>> +   } else {
>>> +      VdpVideoSurfaceGallium *f;
>>> +
>>> +      struct pipe_video_buffer *buffer;
>>> +      struct pipe_sampler_view **samplers;
>>> +
>>> +      if (getProcAddr(device, VDP_FUNC_ID_VIDEO_SURFACE_GALLIUM, 
>>> (void**)&f)) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +         return;
>>> +      }
>>> +
>>> +      buffer = f((uintptr_t)vdpSurface);
>>> +      if (!buffer) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +         return;
>>> +      }
>>> +
>>> +      samplers = buffer->get_sampler_view_planes(buffer);
>>> +      if (!samplers) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +         return;
>>> +      }
>>> +
>>> +      sv = samplers[index >> 1];
>>> +      if (!sv) {
>>> +         _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +         return;
>>> +      }
>>> +
>>> +      res = sv->texture;
>>> +
>>> +      /* In theory we also need to reimport the buffer into the new 
>>> screen,
>>> +         but that currently isn't specified. Just using the resource
>>> +         as it is does indeed seem to work.*/
>>> +   }
>>> +
>>> +   if (!res) {
>>> +      _mesa_error(ctx, GL_INVALID_OPERATION, "VDPAUMapSurfacesNV");
>>> +      return;
>>> +   }
>>> +
>>> +   /* switch to surface based */
>>> +   if (!stObj->surface_based) {
>>> +      _mesa_clear_texture_object(ctx, texObj);
>>> +      stObj->surface_based = GL_TRUE;
>>> +   }
>>> +
>>> +   texFormat = st_pipe_format_to_mesa_format(res->format);
>>> +
>>> +   _mesa_init_teximage_fields(ctx, texImage,
>>> +                              res->width0, res->height0, 1, 0, 
>>> GL_RGBA,
>>> +                              texFormat);
>>> +
>>> +   pipe_resource_reference(&stObj->pt, res);
>>> +   pipe_sampler_view_reference(&stObj->sampler_view, NULL);
>>> +   pipe_resource_reference(&stImage->pt, res);
>>> +
>>> +   u_sampler_view_default_template(&templ, res, res->format);
>>> +   templ.u.tex.first_layer = index & 1;
>>> +   templ.u.tex.last_layer = index & 1;
>>> +   templ.swizzle_r = GET_SWZ(stObj->base._Swizzle, 0);
>>> +   templ.swizzle_g = GET_SWZ(stObj->base._Swizzle, 1);
>>> +   templ.swizzle_b = GET_SWZ(stObj->base._Swizzle, 2);
>>> +   templ.swizzle_a = GET_SWZ(stObj->base._Swizzle, 3);
>>> +   stObj->sampler_view = st->pipe->create_sampler_view(st->pipe, 
>>> res, &templ);
>>> +
>>> +   stObj->width0 = res->width0;
>>> +   stObj->height0 = res->height0;
>>> +   stObj->depth0 = 1;
>>> +   stObj->surface_format = res->format;
>>> +
>>> +   _mesa_dirty_texobj(ctx, texObj, GL_TRUE);
>>> +}
>>> +
>>> +static void
>>> +st_vdpau_unmap_surface(struct gl_context *ctx, GLenum target, 
>>> GLenum access,
>>> +                       GLboolean output, struct gl_texture_object 
>>> *texObj,
>>> +                       struct gl_texture_image *texImage,
>>> +                       const GLvoid *vdpSurface, GLuint index)
>>> +{
>>> +   struct st_texture_object *stObj = st_texture_object(texObj);
>>> +   struct st_texture_image *stImage = st_texture_image(texImage);
>>> +
>>> +   pipe_resource_reference(&stObj->pt, NULL);
>>> +   pipe_sampler_view_reference(&stObj->sampler_view, NULL);
>>> +   pipe_resource_reference(&stImage->pt, NULL);
>>> +
>>> +   _mesa_dirty_texobj(ctx, texObj, GL_TRUE);
>>> +}
>>> +
>>> +void
>>> +st_init_vdpau_functions(struct dd_function_table *functions)
>>> +{
>>> +   functions->VDPAUMapSurface = st_vdpau_map_surface;
>>> +   functions->VDPAUUnmapSurface = st_vdpau_unmap_surface;
>>> +}
>>> diff --git a/src/mesa/state_tracker/st_vdpau.h 
>>> b/src/mesa/state_tracker/st_vdpau.h
>>> new file mode 100644
>>> index 0000000..59c7443
>>> --- /dev/null
>>> +++ b/src/mesa/state_tracker/st_vdpau.h
>>> @@ -0,0 +1,42 @@
>>> +/************************************************************************** 
>>>
>>> + *
>>> + * Copyright 2013 Advanced Micro Devices, Inc.
>>> + * All Rights Reserved.
>>> + *
>>> + * Permission is hereby granted, free of charge, to any person 
>>> obtaining a
>>> + * copy of this software and associated documentation files (the
>>> + * "Software"), to deal in the Software without restriction, including
>>> + * without limitation the rights to use, copy, modify, merge, publish,
>>> + * distribute, sub license, and/or sell copies of the Software, and to
>>> + * permit persons to whom the Software is furnished to do so, 
>>> subject to
>>> + * the following conditions:
>>> + *
>>> + * The above copyright notice and this permission notice (including 
>>> the
>>> + * next paragraph) shall be included in all copies or substantial 
>>> portions
>>> + * of the Software.
>>> + *
>>> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 
>>> EXPRESS
>>> + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
>>> + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 
>>> NON-INFRINGEMENT.
>>> + * IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE 
>>> FOR
>>> + * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF 
>>> CONTRACT,
>>> + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
>>> + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
>>> + *
>>> + 
>>> **************************************************************************/
>>> +
>>> +/*
>>> + * Authors:
>>> + *      Christian König <christian.koenig at amd.com>
>>> + *
>>> + */
>>> +
>>> +#ifndef ST_VDPAU_H
>>> +#define ST_VDPAU_H
>>> +
>>> +struct dd_function_table;
>>> +
>>> +extern void
>>> +st_init_vdpau_functions(struct dd_function_table *functions);
>>> +
>>> +#endif /* ST_VDPAU_H */
>>> -- 
>>> 1.8.1.2
>>>
>>> _______________________________________________
>>> mesa-dev mailing list
>>> mesa-dev at lists.freedesktop.org
>>> http://lists.freedesktop.org/mailman/listinfo/mesa-dev
>
> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/mesa-dev



More information about the mesa-dev mailing list