xref: /aosp_15_r20/external/mesa3d/src/gallium/frontends/vdpau/output.c (revision 6104692788411f58d303aa86923a9ff6ecaded22)
1*61046927SAndroid Build Coastguard Worker /**************************************************************************
2*61046927SAndroid Build Coastguard Worker  *
3*61046927SAndroid Build Coastguard Worker  * Copyright 2010 Thomas Balling Sørensen.
4*61046927SAndroid Build Coastguard Worker  * Copyright 2011 Christian König.
5*61046927SAndroid Build Coastguard Worker  * All Rights Reserved.
6*61046927SAndroid Build Coastguard Worker  *
7*61046927SAndroid Build Coastguard Worker  * Permission is hereby granted, free of charge, to any person obtaining a
8*61046927SAndroid Build Coastguard Worker  * copy of this software and associated documentation files (the
9*61046927SAndroid Build Coastguard Worker  * "Software"), to deal in the Software without restriction, including
10*61046927SAndroid Build Coastguard Worker  * without limitation the rights to use, copy, modify, merge, publish,
11*61046927SAndroid Build Coastguard Worker  * distribute, sub license, and/or sell copies of the Software, and to
12*61046927SAndroid Build Coastguard Worker  * permit persons to whom the Software is furnished to do so, subject to
13*61046927SAndroid Build Coastguard Worker  * the following conditions:
14*61046927SAndroid Build Coastguard Worker  *
15*61046927SAndroid Build Coastguard Worker  * The above copyright notice and this permission notice (including the
16*61046927SAndroid Build Coastguard Worker  * next paragraph) shall be included in all copies or substantial portions
17*61046927SAndroid Build Coastguard Worker  * of the Software.
18*61046927SAndroid Build Coastguard Worker  *
19*61046927SAndroid Build Coastguard Worker  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
20*61046927SAndroid Build Coastguard Worker  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
21*61046927SAndroid Build Coastguard Worker  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
22*61046927SAndroid Build Coastguard Worker  * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
23*61046927SAndroid Build Coastguard Worker  * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
24*61046927SAndroid Build Coastguard Worker  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
25*61046927SAndroid Build Coastguard Worker  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
26*61046927SAndroid Build Coastguard Worker  *
27*61046927SAndroid Build Coastguard Worker  **************************************************************************/
28*61046927SAndroid Build Coastguard Worker 
29*61046927SAndroid Build Coastguard Worker #include <vdpau/vdpau.h>
30*61046927SAndroid Build Coastguard Worker 
31*61046927SAndroid Build Coastguard Worker #include "util/u_debug.h"
32*61046927SAndroid Build Coastguard Worker #include "util/u_memory.h"
33*61046927SAndroid Build Coastguard Worker #include "util/u_sampler.h"
34*61046927SAndroid Build Coastguard Worker #include "util/format/u_format.h"
35*61046927SAndroid Build Coastguard Worker #include "util/u_surface.h"
36*61046927SAndroid Build Coastguard Worker 
37*61046927SAndroid Build Coastguard Worker #include "vl/vl_csc.h"
38*61046927SAndroid Build Coastguard Worker 
39*61046927SAndroid Build Coastguard Worker #include "frontend/drm_driver.h"
40*61046927SAndroid Build Coastguard Worker 
41*61046927SAndroid Build Coastguard Worker #include "vdpau_private.h"
42*61046927SAndroid Build Coastguard Worker 
43*61046927SAndroid Build Coastguard Worker /**
44*61046927SAndroid Build Coastguard Worker  * Create a VdpOutputSurface.
45*61046927SAndroid Build Coastguard Worker  */
46*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfaceCreate(VdpDevice device,VdpRGBAFormat rgba_format,uint32_t width,uint32_t height,VdpOutputSurface * surface)47*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfaceCreate(VdpDevice device,
48*61046927SAndroid Build Coastguard Worker                          VdpRGBAFormat rgba_format,
49*61046927SAndroid Build Coastguard Worker                          uint32_t width, uint32_t height,
50*61046927SAndroid Build Coastguard Worker                          VdpOutputSurface  *surface)
51*61046927SAndroid Build Coastguard Worker {
52*61046927SAndroid Build Coastguard Worker    struct pipe_context *pipe;
53*61046927SAndroid Build Coastguard Worker    struct pipe_resource res_tmpl, *res;
54*61046927SAndroid Build Coastguard Worker    struct pipe_sampler_view sv_templ;
55*61046927SAndroid Build Coastguard Worker    struct pipe_surface surf_templ;
56*61046927SAndroid Build Coastguard Worker 
57*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface = NULL;
58*61046927SAndroid Build Coastguard Worker 
59*61046927SAndroid Build Coastguard Worker    if (!(width && height))
60*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_SIZE;
61*61046927SAndroid Build Coastguard Worker 
62*61046927SAndroid Build Coastguard Worker    vlVdpDevice *dev = vlGetDataHTAB(device);
63*61046927SAndroid Build Coastguard Worker    if (!dev)
64*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
65*61046927SAndroid Build Coastguard Worker 
66*61046927SAndroid Build Coastguard Worker    pipe = dev->context;
67*61046927SAndroid Build Coastguard Worker    if (!pipe)
68*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
69*61046927SAndroid Build Coastguard Worker 
70*61046927SAndroid Build Coastguard Worker    vlsurface = CALLOC(1, sizeof(vlVdpOutputSurface));
71*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
72*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_RESOURCES;
73*61046927SAndroid Build Coastguard Worker 
74*61046927SAndroid Build Coastguard Worker    DeviceReference(&vlsurface->device, dev);
75*61046927SAndroid Build Coastguard Worker 
76*61046927SAndroid Build Coastguard Worker    memset(&res_tmpl, 0, sizeof(res_tmpl));
77*61046927SAndroid Build Coastguard Worker 
78*61046927SAndroid Build Coastguard Worker    /*
79*61046927SAndroid Build Coastguard Worker     * The output won't look correctly when this buffer is send to X,
80*61046927SAndroid Build Coastguard Worker     * if the VDPAU RGB component order doesn't match the X11 one so
81*61046927SAndroid Build Coastguard Worker     * we only allow the X11 format
82*61046927SAndroid Build Coastguard Worker     */
83*61046927SAndroid Build Coastguard Worker    vlsurface->send_to_X = dev->vscreen->color_depth == 24 &&
84*61046927SAndroid Build Coastguard Worker       rgba_format == VDP_RGBA_FORMAT_B8G8R8A8;
85*61046927SAndroid Build Coastguard Worker 
86*61046927SAndroid Build Coastguard Worker    res_tmpl.target = PIPE_TEXTURE_2D;
87*61046927SAndroid Build Coastguard Worker    res_tmpl.format = VdpFormatRGBAToPipe(rgba_format);
88*61046927SAndroid Build Coastguard Worker    res_tmpl.width0 = width;
89*61046927SAndroid Build Coastguard Worker    res_tmpl.height0 = height;
90*61046927SAndroid Build Coastguard Worker    res_tmpl.depth0 = 1;
91*61046927SAndroid Build Coastguard Worker    res_tmpl.array_size = 1;
92*61046927SAndroid Build Coastguard Worker    res_tmpl.bind = PIPE_BIND_SAMPLER_VIEW | PIPE_BIND_RENDER_TARGET |
93*61046927SAndroid Build Coastguard Worker                    PIPE_BIND_SHARED | PIPE_BIND_SCANOUT;
94*61046927SAndroid Build Coastguard Worker    res_tmpl.usage = PIPE_USAGE_DEFAULT;
95*61046927SAndroid Build Coastguard Worker 
96*61046927SAndroid Build Coastguard Worker    mtx_lock(&dev->mutex);
97*61046927SAndroid Build Coastguard Worker 
98*61046927SAndroid Build Coastguard Worker    if (!CheckSurfaceParams(pipe->screen, &res_tmpl))
99*61046927SAndroid Build Coastguard Worker       goto err_unlock;
100*61046927SAndroid Build Coastguard Worker 
101*61046927SAndroid Build Coastguard Worker    res = pipe->screen->resource_create(pipe->screen, &res_tmpl);
102*61046927SAndroid Build Coastguard Worker    if (!res)
103*61046927SAndroid Build Coastguard Worker       goto err_unlock;
104*61046927SAndroid Build Coastguard Worker 
105*61046927SAndroid Build Coastguard Worker    vlVdpDefaultSamplerViewTemplate(&sv_templ, res);
106*61046927SAndroid Build Coastguard Worker    vlsurface->sampler_view = pipe->create_sampler_view(pipe, res, &sv_templ);
107*61046927SAndroid Build Coastguard Worker    if (!vlsurface->sampler_view)
108*61046927SAndroid Build Coastguard Worker       goto err_resource;
109*61046927SAndroid Build Coastguard Worker 
110*61046927SAndroid Build Coastguard Worker    memset(&surf_templ, 0, sizeof(surf_templ));
111*61046927SAndroid Build Coastguard Worker    surf_templ.format = res->format;
112*61046927SAndroid Build Coastguard Worker    vlsurface->surface = pipe->create_surface(pipe, res, &surf_templ);
113*61046927SAndroid Build Coastguard Worker    if (!vlsurface->surface)
114*61046927SAndroid Build Coastguard Worker       goto err_resource;
115*61046927SAndroid Build Coastguard Worker 
116*61046927SAndroid Build Coastguard Worker    *surface = vlAddDataHTAB(vlsurface);
117*61046927SAndroid Build Coastguard Worker    if (*surface == 0)
118*61046927SAndroid Build Coastguard Worker       goto err_resource;
119*61046927SAndroid Build Coastguard Worker 
120*61046927SAndroid Build Coastguard Worker    pipe_resource_reference(&res, NULL);
121*61046927SAndroid Build Coastguard Worker 
122*61046927SAndroid Build Coastguard Worker    if (!vl_compositor_init_state(&vlsurface->cstate, pipe))
123*61046927SAndroid Build Coastguard Worker       goto err_resource;
124*61046927SAndroid Build Coastguard Worker 
125*61046927SAndroid Build Coastguard Worker    vl_compositor_reset_dirty_area(&vlsurface->dirty_area);
126*61046927SAndroid Build Coastguard Worker    mtx_unlock(&dev->mutex);
127*61046927SAndroid Build Coastguard Worker 
128*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
129*61046927SAndroid Build Coastguard Worker 
130*61046927SAndroid Build Coastguard Worker err_resource:
131*61046927SAndroid Build Coastguard Worker    pipe_sampler_view_reference(&vlsurface->sampler_view, NULL);
132*61046927SAndroid Build Coastguard Worker    pipe_surface_reference(&vlsurface->surface, NULL);
133*61046927SAndroid Build Coastguard Worker    pipe_resource_reference(&res, NULL);
134*61046927SAndroid Build Coastguard Worker err_unlock:
135*61046927SAndroid Build Coastguard Worker    mtx_unlock(&dev->mutex);
136*61046927SAndroid Build Coastguard Worker    DeviceReference(&vlsurface->device, NULL);
137*61046927SAndroid Build Coastguard Worker    FREE(vlsurface);
138*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_ERROR;
139*61046927SAndroid Build Coastguard Worker }
140*61046927SAndroid Build Coastguard Worker 
141*61046927SAndroid Build Coastguard Worker /**
142*61046927SAndroid Build Coastguard Worker  * Destroy a VdpOutputSurface.
143*61046927SAndroid Build Coastguard Worker  */
144*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfaceDestroy(VdpOutputSurface surface)145*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfaceDestroy(VdpOutputSurface surface)
146*61046927SAndroid Build Coastguard Worker {
147*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
148*61046927SAndroid Build Coastguard Worker    struct pipe_context *pipe;
149*61046927SAndroid Build Coastguard Worker 
150*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
151*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
152*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
153*61046927SAndroid Build Coastguard Worker 
154*61046927SAndroid Build Coastguard Worker    pipe = vlsurface->device->context;
155*61046927SAndroid Build Coastguard Worker 
156*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
157*61046927SAndroid Build Coastguard Worker 
158*61046927SAndroid Build Coastguard Worker    pipe_surface_reference(&vlsurface->surface, NULL);
159*61046927SAndroid Build Coastguard Worker    pipe_sampler_view_reference(&vlsurface->sampler_view, NULL);
160*61046927SAndroid Build Coastguard Worker    pipe->screen->fence_reference(pipe->screen, &vlsurface->fence, NULL);
161*61046927SAndroid Build Coastguard Worker    vl_compositor_cleanup_state(&vlsurface->cstate);
162*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
163*61046927SAndroid Build Coastguard Worker 
164*61046927SAndroid Build Coastguard Worker    vlRemoveDataHTAB(surface);
165*61046927SAndroid Build Coastguard Worker    DeviceReference(&vlsurface->device, NULL);
166*61046927SAndroid Build Coastguard Worker    FREE(vlsurface);
167*61046927SAndroid Build Coastguard Worker 
168*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
169*61046927SAndroid Build Coastguard Worker }
170*61046927SAndroid Build Coastguard Worker 
171*61046927SAndroid Build Coastguard Worker /**
172*61046927SAndroid Build Coastguard Worker  * Retrieve the parameters used to create a VdpOutputSurface.
173*61046927SAndroid Build Coastguard Worker  */
174*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfaceGetParameters(VdpOutputSurface surface,VdpRGBAFormat * rgba_format,uint32_t * width,uint32_t * height)175*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfaceGetParameters(VdpOutputSurface surface,
176*61046927SAndroid Build Coastguard Worker                                 VdpRGBAFormat *rgba_format,
177*61046927SAndroid Build Coastguard Worker                                 uint32_t *width, uint32_t *height)
178*61046927SAndroid Build Coastguard Worker {
179*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
180*61046927SAndroid Build Coastguard Worker 
181*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
182*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
183*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
184*61046927SAndroid Build Coastguard Worker 
185*61046927SAndroid Build Coastguard Worker    *rgba_format = PipeToFormatRGBA(vlsurface->sampler_view->texture->format);
186*61046927SAndroid Build Coastguard Worker    *width = vlsurface->sampler_view->texture->width0;
187*61046927SAndroid Build Coastguard Worker    *height = vlsurface->sampler_view->texture->height0;
188*61046927SAndroid Build Coastguard Worker 
189*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
190*61046927SAndroid Build Coastguard Worker }
191*61046927SAndroid Build Coastguard Worker 
192*61046927SAndroid Build Coastguard Worker /**
193*61046927SAndroid Build Coastguard Worker  * Copy image data from a VdpOutputSurface to application memory in the
194*61046927SAndroid Build Coastguard Worker  * surface's native format.
195*61046927SAndroid Build Coastguard Worker  */
196*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfaceGetBitsNative(VdpOutputSurface surface,VdpRect const * source_rect,void * const * destination_data,uint32_t const * destination_pitches)197*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfaceGetBitsNative(VdpOutputSurface surface,
198*61046927SAndroid Build Coastguard Worker                                 VdpRect const *source_rect,
199*61046927SAndroid Build Coastguard Worker                                 void *const *destination_data,
200*61046927SAndroid Build Coastguard Worker                                 uint32_t const *destination_pitches)
201*61046927SAndroid Build Coastguard Worker {
202*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
203*61046927SAndroid Build Coastguard Worker    struct pipe_context *pipe;
204*61046927SAndroid Build Coastguard Worker    struct pipe_resource *res;
205*61046927SAndroid Build Coastguard Worker    struct pipe_box box;
206*61046927SAndroid Build Coastguard Worker    struct pipe_transfer *transfer;
207*61046927SAndroid Build Coastguard Worker    uint8_t *map;
208*61046927SAndroid Build Coastguard Worker 
209*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
210*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
211*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
212*61046927SAndroid Build Coastguard Worker 
213*61046927SAndroid Build Coastguard Worker    pipe = vlsurface->device->context;
214*61046927SAndroid Build Coastguard Worker    if (!pipe)
215*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
216*61046927SAndroid Build Coastguard Worker 
217*61046927SAndroid Build Coastguard Worker    if (!destination_data || !destination_pitches)
218*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_POINTER;
219*61046927SAndroid Build Coastguard Worker 
220*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
221*61046927SAndroid Build Coastguard Worker 
222*61046927SAndroid Build Coastguard Worker    res = vlsurface->sampler_view->texture;
223*61046927SAndroid Build Coastguard Worker    box = RectToPipeBox(source_rect, res);
224*61046927SAndroid Build Coastguard Worker    map = pipe->texture_map(pipe, res, 0, PIPE_MAP_READ, &box, &transfer);
225*61046927SAndroid Build Coastguard Worker    if (!map) {
226*61046927SAndroid Build Coastguard Worker       mtx_unlock(&vlsurface->device->mutex);
227*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_RESOURCES;
228*61046927SAndroid Build Coastguard Worker    }
229*61046927SAndroid Build Coastguard Worker 
230*61046927SAndroid Build Coastguard Worker    util_copy_rect(*destination_data, res->format, *destination_pitches, 0, 0,
231*61046927SAndroid Build Coastguard Worker                   box.width, box.height, map, transfer->stride, 0, 0);
232*61046927SAndroid Build Coastguard Worker 
233*61046927SAndroid Build Coastguard Worker    pipe_texture_unmap(pipe, transfer);
234*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
235*61046927SAndroid Build Coastguard Worker 
236*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
237*61046927SAndroid Build Coastguard Worker }
238*61046927SAndroid Build Coastguard Worker 
239*61046927SAndroid Build Coastguard Worker /**
240*61046927SAndroid Build Coastguard Worker  * Copy image data from application memory in the surface's native format to
241*61046927SAndroid Build Coastguard Worker  * a VdpOutputSurface.
242*61046927SAndroid Build Coastguard Worker  */
243*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfacePutBitsNative(VdpOutputSurface surface,void const * const * source_data,uint32_t const * source_pitches,VdpRect const * destination_rect)244*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfacePutBitsNative(VdpOutputSurface surface,
245*61046927SAndroid Build Coastguard Worker                                 void const *const *source_data,
246*61046927SAndroid Build Coastguard Worker                                 uint32_t const *source_pitches,
247*61046927SAndroid Build Coastguard Worker                                 VdpRect const *destination_rect)
248*61046927SAndroid Build Coastguard Worker {
249*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
250*61046927SAndroid Build Coastguard Worker    struct pipe_box dst_box;
251*61046927SAndroid Build Coastguard Worker    struct pipe_context *pipe;
252*61046927SAndroid Build Coastguard Worker 
253*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
254*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
255*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
256*61046927SAndroid Build Coastguard Worker 
257*61046927SAndroid Build Coastguard Worker    pipe = vlsurface->device->context;
258*61046927SAndroid Build Coastguard Worker    if (!pipe)
259*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
260*61046927SAndroid Build Coastguard Worker 
261*61046927SAndroid Build Coastguard Worker    if (!source_data || !source_pitches)
262*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_POINTER;
263*61046927SAndroid Build Coastguard Worker 
264*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
265*61046927SAndroid Build Coastguard Worker 
266*61046927SAndroid Build Coastguard Worker    dst_box = RectToPipeBox(destination_rect, vlsurface->sampler_view->texture);
267*61046927SAndroid Build Coastguard Worker 
268*61046927SAndroid Build Coastguard Worker    /* Check for a no-op. (application bug?) */
269*61046927SAndroid Build Coastguard Worker    if (!dst_box.width || !dst_box.height) {
270*61046927SAndroid Build Coastguard Worker       mtx_unlock(&vlsurface->device->mutex);
271*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_OK;
272*61046927SAndroid Build Coastguard Worker    }
273*61046927SAndroid Build Coastguard Worker 
274*61046927SAndroid Build Coastguard Worker    pipe->texture_subdata(pipe, vlsurface->sampler_view->texture, 0,
275*61046927SAndroid Build Coastguard Worker                          PIPE_MAP_WRITE, &dst_box, *source_data,
276*61046927SAndroid Build Coastguard Worker                          *source_pitches, 0);
277*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
278*61046927SAndroid Build Coastguard Worker 
279*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
280*61046927SAndroid Build Coastguard Worker }
281*61046927SAndroid Build Coastguard Worker 
282*61046927SAndroid Build Coastguard Worker /**
283*61046927SAndroid Build Coastguard Worker  * Copy image data from application memory in a specific indexed format to
284*61046927SAndroid Build Coastguard Worker  * a VdpOutputSurface.
285*61046927SAndroid Build Coastguard Worker  */
286*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfacePutBitsIndexed(VdpOutputSurface surface,VdpIndexedFormat source_indexed_format,void const * const * source_data,uint32_t const * source_pitch,VdpRect const * destination_rect,VdpColorTableFormat color_table_format,void const * color_table)287*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfacePutBitsIndexed(VdpOutputSurface surface,
288*61046927SAndroid Build Coastguard Worker                                  VdpIndexedFormat source_indexed_format,
289*61046927SAndroid Build Coastguard Worker                                  void const *const *source_data,
290*61046927SAndroid Build Coastguard Worker                                  uint32_t const *source_pitch,
291*61046927SAndroid Build Coastguard Worker                                  VdpRect const *destination_rect,
292*61046927SAndroid Build Coastguard Worker                                  VdpColorTableFormat color_table_format,
293*61046927SAndroid Build Coastguard Worker                                  void const *color_table)
294*61046927SAndroid Build Coastguard Worker {
295*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
296*61046927SAndroid Build Coastguard Worker    struct pipe_context *context;
297*61046927SAndroid Build Coastguard Worker    struct vl_compositor *compositor;
298*61046927SAndroid Build Coastguard Worker    struct vl_compositor_state *cstate;
299*61046927SAndroid Build Coastguard Worker 
300*61046927SAndroid Build Coastguard Worker    enum pipe_format index_format;
301*61046927SAndroid Build Coastguard Worker    enum pipe_format colortbl_format;
302*61046927SAndroid Build Coastguard Worker 
303*61046927SAndroid Build Coastguard Worker    struct pipe_resource *res, res_tmpl;
304*61046927SAndroid Build Coastguard Worker    struct pipe_sampler_view sv_tmpl;
305*61046927SAndroid Build Coastguard Worker    struct pipe_sampler_view *sv_idx = NULL, *sv_tbl = NULL;
306*61046927SAndroid Build Coastguard Worker 
307*61046927SAndroid Build Coastguard Worker    struct pipe_box box;
308*61046927SAndroid Build Coastguard Worker    struct u_rect dst_rect;
309*61046927SAndroid Build Coastguard Worker 
310*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
311*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
312*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
313*61046927SAndroid Build Coastguard Worker 
314*61046927SAndroid Build Coastguard Worker    context = vlsurface->device->context;
315*61046927SAndroid Build Coastguard Worker    compositor = &vlsurface->device->compositor;
316*61046927SAndroid Build Coastguard Worker    cstate = &vlsurface->cstate;
317*61046927SAndroid Build Coastguard Worker 
318*61046927SAndroid Build Coastguard Worker    index_format = FormatIndexedToPipe(source_indexed_format);
319*61046927SAndroid Build Coastguard Worker    if (index_format == PIPE_FORMAT_NONE)
320*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_INDEXED_FORMAT;
321*61046927SAndroid Build Coastguard Worker 
322*61046927SAndroid Build Coastguard Worker    if (!source_data || !source_pitch)
323*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_POINTER;
324*61046927SAndroid Build Coastguard Worker 
325*61046927SAndroid Build Coastguard Worker    colortbl_format = FormatColorTableToPipe(color_table_format);
326*61046927SAndroid Build Coastguard Worker    if (colortbl_format == PIPE_FORMAT_NONE)
327*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_COLOR_TABLE_FORMAT;
328*61046927SAndroid Build Coastguard Worker 
329*61046927SAndroid Build Coastguard Worker    if (!color_table)
330*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_POINTER;
331*61046927SAndroid Build Coastguard Worker 
332*61046927SAndroid Build Coastguard Worker    memset(&res_tmpl, 0, sizeof(res_tmpl));
333*61046927SAndroid Build Coastguard Worker    res_tmpl.target = PIPE_TEXTURE_2D;
334*61046927SAndroid Build Coastguard Worker    res_tmpl.format = index_format;
335*61046927SAndroid Build Coastguard Worker 
336*61046927SAndroid Build Coastguard Worker    if (destination_rect) {
337*61046927SAndroid Build Coastguard Worker       if (destination_rect->x1 > destination_rect->x0 &&
338*61046927SAndroid Build Coastguard Worker           destination_rect->y1 > destination_rect->y0) {
339*61046927SAndroid Build Coastguard Worker          res_tmpl.width0 = destination_rect->x1 - destination_rect->x0;
340*61046927SAndroid Build Coastguard Worker          res_tmpl.height0 = destination_rect->y1 - destination_rect->y0;
341*61046927SAndroid Build Coastguard Worker       }
342*61046927SAndroid Build Coastguard Worker    } else {
343*61046927SAndroid Build Coastguard Worker       res_tmpl.width0 = vlsurface->surface->texture->width0;
344*61046927SAndroid Build Coastguard Worker       res_tmpl.height0 = vlsurface->surface->texture->height0;
345*61046927SAndroid Build Coastguard Worker    }
346*61046927SAndroid Build Coastguard Worker    res_tmpl.depth0 = 1;
347*61046927SAndroid Build Coastguard Worker    res_tmpl.array_size = 1;
348*61046927SAndroid Build Coastguard Worker    res_tmpl.usage = PIPE_USAGE_STAGING;
349*61046927SAndroid Build Coastguard Worker    res_tmpl.bind = PIPE_BIND_SAMPLER_VIEW;
350*61046927SAndroid Build Coastguard Worker 
351*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
352*61046927SAndroid Build Coastguard Worker 
353*61046927SAndroid Build Coastguard Worker    if (!CheckSurfaceParams(context->screen, &res_tmpl))
354*61046927SAndroid Build Coastguard Worker       goto error_resource;
355*61046927SAndroid Build Coastguard Worker 
356*61046927SAndroid Build Coastguard Worker    res = context->screen->resource_create(context->screen, &res_tmpl);
357*61046927SAndroid Build Coastguard Worker    if (!res)
358*61046927SAndroid Build Coastguard Worker       goto error_resource;
359*61046927SAndroid Build Coastguard Worker 
360*61046927SAndroid Build Coastguard Worker    box.x = box.y = box.z = 0;
361*61046927SAndroid Build Coastguard Worker    box.width = res->width0;
362*61046927SAndroid Build Coastguard Worker    box.height = res->height0;
363*61046927SAndroid Build Coastguard Worker    box.depth = res->depth0;
364*61046927SAndroid Build Coastguard Worker 
365*61046927SAndroid Build Coastguard Worker    context->texture_subdata(context, res, 0, PIPE_MAP_WRITE, &box,
366*61046927SAndroid Build Coastguard Worker                             source_data[0], source_pitch[0],
367*61046927SAndroid Build Coastguard Worker                             source_pitch[0] * res->height0);
368*61046927SAndroid Build Coastguard Worker 
369*61046927SAndroid Build Coastguard Worker    memset(&sv_tmpl, 0, sizeof(sv_tmpl));
370*61046927SAndroid Build Coastguard Worker    u_sampler_view_default_template(&sv_tmpl, res, res->format);
371*61046927SAndroid Build Coastguard Worker 
372*61046927SAndroid Build Coastguard Worker    sv_idx = context->create_sampler_view(context, res, &sv_tmpl);
373*61046927SAndroid Build Coastguard Worker    pipe_resource_reference(&res, NULL);
374*61046927SAndroid Build Coastguard Worker 
375*61046927SAndroid Build Coastguard Worker    if (!sv_idx)
376*61046927SAndroid Build Coastguard Worker       goto error_resource;
377*61046927SAndroid Build Coastguard Worker 
378*61046927SAndroid Build Coastguard Worker    memset(&res_tmpl, 0, sizeof(res_tmpl));
379*61046927SAndroid Build Coastguard Worker    res_tmpl.target = PIPE_TEXTURE_1D;
380*61046927SAndroid Build Coastguard Worker    res_tmpl.format = colortbl_format;
381*61046927SAndroid Build Coastguard Worker    res_tmpl.width0 = 1 << util_format_get_component_bits(
382*61046927SAndroid Build Coastguard Worker       index_format, UTIL_FORMAT_COLORSPACE_RGB, 0);
383*61046927SAndroid Build Coastguard Worker    res_tmpl.height0 = 1;
384*61046927SAndroid Build Coastguard Worker    res_tmpl.depth0 = 1;
385*61046927SAndroid Build Coastguard Worker    res_tmpl.array_size = 1;
386*61046927SAndroid Build Coastguard Worker    res_tmpl.usage = PIPE_USAGE_STAGING;
387*61046927SAndroid Build Coastguard Worker    res_tmpl.bind = PIPE_BIND_SAMPLER_VIEW;
388*61046927SAndroid Build Coastguard Worker 
389*61046927SAndroid Build Coastguard Worker    res = context->screen->resource_create(context->screen, &res_tmpl);
390*61046927SAndroid Build Coastguard Worker    if (!res)
391*61046927SAndroid Build Coastguard Worker       goto error_resource;
392*61046927SAndroid Build Coastguard Worker 
393*61046927SAndroid Build Coastguard Worker    box.x = box.y = box.z = 0;
394*61046927SAndroid Build Coastguard Worker    box.width = res->width0;
395*61046927SAndroid Build Coastguard Worker    box.height = res->height0;
396*61046927SAndroid Build Coastguard Worker    box.depth = res->depth0;
397*61046927SAndroid Build Coastguard Worker 
398*61046927SAndroid Build Coastguard Worker    context->texture_subdata(context, res, 0, PIPE_MAP_WRITE, &box, color_table,
399*61046927SAndroid Build Coastguard Worker                             util_format_get_stride(colortbl_format, res->width0), 0);
400*61046927SAndroid Build Coastguard Worker 
401*61046927SAndroid Build Coastguard Worker    memset(&sv_tmpl, 0, sizeof(sv_tmpl));
402*61046927SAndroid Build Coastguard Worker    u_sampler_view_default_template(&sv_tmpl, res, res->format);
403*61046927SAndroid Build Coastguard Worker 
404*61046927SAndroid Build Coastguard Worker    sv_tbl = context->create_sampler_view(context, res, &sv_tmpl);
405*61046927SAndroid Build Coastguard Worker    pipe_resource_reference(&res, NULL);
406*61046927SAndroid Build Coastguard Worker 
407*61046927SAndroid Build Coastguard Worker    if (!sv_tbl)
408*61046927SAndroid Build Coastguard Worker       goto error_resource;
409*61046927SAndroid Build Coastguard Worker 
410*61046927SAndroid Build Coastguard Worker    vl_compositor_clear_layers(cstate);
411*61046927SAndroid Build Coastguard Worker    vl_compositor_set_palette_layer(cstate, compositor, 0, sv_idx, sv_tbl, NULL, NULL, false);
412*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_dst_area(cstate, 0, RectToPipe(destination_rect, &dst_rect));
413*61046927SAndroid Build Coastguard Worker    vl_compositor_render(cstate, compositor, vlsurface->surface, &vlsurface->dirty_area, false);
414*61046927SAndroid Build Coastguard Worker 
415*61046927SAndroid Build Coastguard Worker    pipe_sampler_view_reference(&sv_idx, NULL);
416*61046927SAndroid Build Coastguard Worker    pipe_sampler_view_reference(&sv_tbl, NULL);
417*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
418*61046927SAndroid Build Coastguard Worker 
419*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
420*61046927SAndroid Build Coastguard Worker 
421*61046927SAndroid Build Coastguard Worker error_resource:
422*61046927SAndroid Build Coastguard Worker    pipe_sampler_view_reference(&sv_idx, NULL);
423*61046927SAndroid Build Coastguard Worker    pipe_sampler_view_reference(&sv_tbl, NULL);
424*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
425*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_RESOURCES;
426*61046927SAndroid Build Coastguard Worker }
427*61046927SAndroid Build Coastguard Worker 
428*61046927SAndroid Build Coastguard Worker /**
429*61046927SAndroid Build Coastguard Worker  * Copy image data from application memory in a specific YCbCr format to
430*61046927SAndroid Build Coastguard Worker  * a VdpOutputSurface.
431*61046927SAndroid Build Coastguard Worker  */
432*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfacePutBitsYCbCr(VdpOutputSurface surface,VdpYCbCrFormat source_ycbcr_format,void const * const * source_data,uint32_t const * source_pitches,VdpRect const * destination_rect,VdpCSCMatrix const * csc_matrix)433*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfacePutBitsYCbCr(VdpOutputSurface surface,
434*61046927SAndroid Build Coastguard Worker                                VdpYCbCrFormat source_ycbcr_format,
435*61046927SAndroid Build Coastguard Worker                                void const *const *source_data,
436*61046927SAndroid Build Coastguard Worker                                uint32_t const *source_pitches,
437*61046927SAndroid Build Coastguard Worker                                VdpRect const *destination_rect,
438*61046927SAndroid Build Coastguard Worker                                VdpCSCMatrix const *csc_matrix)
439*61046927SAndroid Build Coastguard Worker {
440*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
441*61046927SAndroid Build Coastguard Worker    struct vl_compositor *compositor;
442*61046927SAndroid Build Coastguard Worker    struct vl_compositor_state *cstate;
443*61046927SAndroid Build Coastguard Worker 
444*61046927SAndroid Build Coastguard Worker    struct pipe_context *pipe;
445*61046927SAndroid Build Coastguard Worker    enum pipe_format format;
446*61046927SAndroid Build Coastguard Worker    struct pipe_video_buffer vtmpl, *vbuffer;
447*61046927SAndroid Build Coastguard Worker    struct u_rect dst_rect;
448*61046927SAndroid Build Coastguard Worker    struct pipe_sampler_view **sampler_views;
449*61046927SAndroid Build Coastguard Worker 
450*61046927SAndroid Build Coastguard Worker    unsigned i;
451*61046927SAndroid Build Coastguard Worker 
452*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
453*61046927SAndroid Build Coastguard Worker    if (!vlsurface)
454*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
455*61046927SAndroid Build Coastguard Worker 
456*61046927SAndroid Build Coastguard Worker 
457*61046927SAndroid Build Coastguard Worker    pipe = vlsurface->device->context;
458*61046927SAndroid Build Coastguard Worker    compositor = &vlsurface->device->compositor;
459*61046927SAndroid Build Coastguard Worker    cstate = &vlsurface->cstate;
460*61046927SAndroid Build Coastguard Worker 
461*61046927SAndroid Build Coastguard Worker    format = FormatYCBCRToPipe(source_ycbcr_format);
462*61046927SAndroid Build Coastguard Worker    if (format == PIPE_FORMAT_NONE)
463*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_Y_CB_CR_FORMAT;
464*61046927SAndroid Build Coastguard Worker 
465*61046927SAndroid Build Coastguard Worker    if (!source_data || !source_pitches)
466*61046927SAndroid Build Coastguard Worker        return VDP_STATUS_INVALID_POINTER;
467*61046927SAndroid Build Coastguard Worker 
468*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
469*61046927SAndroid Build Coastguard Worker    memset(&vtmpl, 0, sizeof(vtmpl));
470*61046927SAndroid Build Coastguard Worker    vtmpl.buffer_format = format;
471*61046927SAndroid Build Coastguard Worker 
472*61046927SAndroid Build Coastguard Worker    if (destination_rect) {
473*61046927SAndroid Build Coastguard Worker       if (destination_rect->x1 > destination_rect->x0 &&
474*61046927SAndroid Build Coastguard Worker           destination_rect->y1 > destination_rect->y0) {
475*61046927SAndroid Build Coastguard Worker          vtmpl.width = destination_rect->x1 - destination_rect->x0;
476*61046927SAndroid Build Coastguard Worker          vtmpl.height = destination_rect->y1 - destination_rect->y0;
477*61046927SAndroid Build Coastguard Worker       }
478*61046927SAndroid Build Coastguard Worker    } else {
479*61046927SAndroid Build Coastguard Worker       vtmpl.width = vlsurface->surface->texture->width0;
480*61046927SAndroid Build Coastguard Worker       vtmpl.height = vlsurface->surface->texture->height0;
481*61046927SAndroid Build Coastguard Worker    }
482*61046927SAndroid Build Coastguard Worker 
483*61046927SAndroid Build Coastguard Worker    vbuffer = pipe->create_video_buffer(pipe, &vtmpl);
484*61046927SAndroid Build Coastguard Worker    if (!vbuffer) {
485*61046927SAndroid Build Coastguard Worker       mtx_unlock(&vlsurface->device->mutex);
486*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_RESOURCES;
487*61046927SAndroid Build Coastguard Worker    }
488*61046927SAndroid Build Coastguard Worker 
489*61046927SAndroid Build Coastguard Worker    sampler_views = vbuffer->get_sampler_view_planes(vbuffer);
490*61046927SAndroid Build Coastguard Worker    if (!sampler_views) {
491*61046927SAndroid Build Coastguard Worker       vbuffer->destroy(vbuffer);
492*61046927SAndroid Build Coastguard Worker       mtx_unlock(&vlsurface->device->mutex);
493*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_RESOURCES;
494*61046927SAndroid Build Coastguard Worker    }
495*61046927SAndroid Build Coastguard Worker 
496*61046927SAndroid Build Coastguard Worker    for (i = 0; i < 3; ++i) {
497*61046927SAndroid Build Coastguard Worker       struct pipe_sampler_view *sv = sampler_views[i];
498*61046927SAndroid Build Coastguard Worker       if (!sv) continue;
499*61046927SAndroid Build Coastguard Worker 
500*61046927SAndroid Build Coastguard Worker       struct pipe_box dst_box;
501*61046927SAndroid Build Coastguard Worker       u_box_3d(0, 0, 0,
502*61046927SAndroid Build Coastguard Worker                sv->texture->width0, sv->texture->height0, 1, &dst_box);
503*61046927SAndroid Build Coastguard Worker 
504*61046927SAndroid Build Coastguard Worker       pipe->texture_subdata(pipe, sv->texture, 0, PIPE_MAP_WRITE, &dst_box,
505*61046927SAndroid Build Coastguard Worker                             source_data[i], source_pitches[i], 0);
506*61046927SAndroid Build Coastguard Worker    }
507*61046927SAndroid Build Coastguard Worker 
508*61046927SAndroid Build Coastguard Worker    if (!csc_matrix) {
509*61046927SAndroid Build Coastguard Worker       vl_csc_matrix csc;
510*61046927SAndroid Build Coastguard Worker       vl_csc_get_matrix(VL_CSC_COLOR_STANDARD_BT_601, NULL, 1, &csc);
511*61046927SAndroid Build Coastguard Worker       if (!vl_compositor_set_csc_matrix(cstate, (const vl_csc_matrix*)&csc, 1.0f, 0.0f))
512*61046927SAndroid Build Coastguard Worker          goto err_csc_matrix;
513*61046927SAndroid Build Coastguard Worker    } else {
514*61046927SAndroid Build Coastguard Worker       if (!vl_compositor_set_csc_matrix(cstate, csc_matrix, 1.0f, 0.0f))
515*61046927SAndroid Build Coastguard Worker          goto err_csc_matrix;
516*61046927SAndroid Build Coastguard Worker    }
517*61046927SAndroid Build Coastguard Worker 
518*61046927SAndroid Build Coastguard Worker    vl_compositor_clear_layers(cstate);
519*61046927SAndroid Build Coastguard Worker    vl_compositor_set_buffer_layer(cstate, compositor, 0, vbuffer, NULL, NULL, VL_COMPOSITOR_WEAVE);
520*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_dst_area(cstate, 0, RectToPipe(destination_rect, &dst_rect));
521*61046927SAndroid Build Coastguard Worker    vl_compositor_render(cstate, compositor, vlsurface->surface, &vlsurface->dirty_area, false);
522*61046927SAndroid Build Coastguard Worker 
523*61046927SAndroid Build Coastguard Worker    vbuffer->destroy(vbuffer);
524*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
525*61046927SAndroid Build Coastguard Worker 
526*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
527*61046927SAndroid Build Coastguard Worker err_csc_matrix:
528*61046927SAndroid Build Coastguard Worker    vbuffer->destroy(vbuffer);
529*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
530*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_ERROR;
531*61046927SAndroid Build Coastguard Worker }
532*61046927SAndroid Build Coastguard Worker 
533*61046927SAndroid Build Coastguard Worker static unsigned
BlendFactorToPipe(VdpOutputSurfaceRenderBlendFactor factor)534*61046927SAndroid Build Coastguard Worker BlendFactorToPipe(VdpOutputSurfaceRenderBlendFactor factor)
535*61046927SAndroid Build Coastguard Worker {
536*61046927SAndroid Build Coastguard Worker    switch (factor) {
537*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ZERO:
538*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_ZERO;
539*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE:
540*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_ONE;
541*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_SRC_COLOR:
542*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_SRC_COLOR;
543*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE_MINUS_SRC_COLOR:
544*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_INV_SRC_COLOR;
545*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_SRC_ALPHA:
546*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_SRC_ALPHA;
547*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA:
548*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_INV_SRC_ALPHA;
549*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_DST_ALPHA:
550*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_DST_ALPHA;
551*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE_MINUS_DST_ALPHA:
552*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_INV_DST_ALPHA;
553*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_DST_COLOR:
554*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_DST_COLOR;
555*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE_MINUS_DST_COLOR:
556*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_INV_DST_COLOR;
557*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_SRC_ALPHA_SATURATE:
558*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_SRC_ALPHA_SATURATE;
559*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_CONSTANT_COLOR:
560*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_CONST_COLOR;
561*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE_MINUS_CONSTANT_COLOR:
562*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_INV_CONST_COLOR;
563*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_CONSTANT_ALPHA:
564*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_CONST_ALPHA;
565*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_FACTOR_ONE_MINUS_CONSTANT_ALPHA:
566*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_INV_CONST_ALPHA;
567*61046927SAndroid Build Coastguard Worker    default:
568*61046927SAndroid Build Coastguard Worker       assert(0);
569*61046927SAndroid Build Coastguard Worker       return PIPE_BLENDFACTOR_ONE;
570*61046927SAndroid Build Coastguard Worker    }
571*61046927SAndroid Build Coastguard Worker }
572*61046927SAndroid Build Coastguard Worker 
573*61046927SAndroid Build Coastguard Worker static unsigned
BlendEquationToPipe(VdpOutputSurfaceRenderBlendEquation equation)574*61046927SAndroid Build Coastguard Worker BlendEquationToPipe(VdpOutputSurfaceRenderBlendEquation equation)
575*61046927SAndroid Build Coastguard Worker {
576*61046927SAndroid Build Coastguard Worker    switch (equation) {
577*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_EQUATION_SUBTRACT:
578*61046927SAndroid Build Coastguard Worker       return PIPE_BLEND_SUBTRACT;
579*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_EQUATION_REVERSE_SUBTRACT:
580*61046927SAndroid Build Coastguard Worker       return PIPE_BLEND_REVERSE_SUBTRACT;
581*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_EQUATION_ADD:
582*61046927SAndroid Build Coastguard Worker       return PIPE_BLEND_ADD;
583*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_EQUATION_MIN:
584*61046927SAndroid Build Coastguard Worker       return PIPE_BLEND_MIN;
585*61046927SAndroid Build Coastguard Worker    case VDP_OUTPUT_SURFACE_RENDER_BLEND_EQUATION_MAX:
586*61046927SAndroid Build Coastguard Worker       return PIPE_BLEND_MAX;
587*61046927SAndroid Build Coastguard Worker    default:
588*61046927SAndroid Build Coastguard Worker       assert(0);
589*61046927SAndroid Build Coastguard Worker       return PIPE_BLEND_ADD;
590*61046927SAndroid Build Coastguard Worker    }
591*61046927SAndroid Build Coastguard Worker }
592*61046927SAndroid Build Coastguard Worker 
593*61046927SAndroid Build Coastguard Worker static void *
BlenderToPipe(struct pipe_context * context,VdpOutputSurfaceRenderBlendState const * blend_state)594*61046927SAndroid Build Coastguard Worker BlenderToPipe(struct pipe_context *context,
595*61046927SAndroid Build Coastguard Worker               VdpOutputSurfaceRenderBlendState const *blend_state)
596*61046927SAndroid Build Coastguard Worker {
597*61046927SAndroid Build Coastguard Worker    struct pipe_blend_state blend;
598*61046927SAndroid Build Coastguard Worker 
599*61046927SAndroid Build Coastguard Worker    memset(&blend, 0, sizeof blend);
600*61046927SAndroid Build Coastguard Worker    blend.independent_blend_enable = 0;
601*61046927SAndroid Build Coastguard Worker 
602*61046927SAndroid Build Coastguard Worker    if (blend_state) {
603*61046927SAndroid Build Coastguard Worker       blend.rt[0].blend_enable = 1;
604*61046927SAndroid Build Coastguard Worker       blend.rt[0].rgb_src_factor = BlendFactorToPipe(blend_state->blend_factor_source_color);
605*61046927SAndroid Build Coastguard Worker       blend.rt[0].rgb_dst_factor = BlendFactorToPipe(blend_state->blend_factor_destination_color);
606*61046927SAndroid Build Coastguard Worker       blend.rt[0].alpha_src_factor = BlendFactorToPipe(blend_state->blend_factor_source_alpha);
607*61046927SAndroid Build Coastguard Worker       blend.rt[0].alpha_dst_factor = BlendFactorToPipe(blend_state->blend_factor_destination_alpha);
608*61046927SAndroid Build Coastguard Worker       blend.rt[0].rgb_func = BlendEquationToPipe(blend_state->blend_equation_color);
609*61046927SAndroid Build Coastguard Worker       blend.rt[0].alpha_func = BlendEquationToPipe(blend_state->blend_equation_alpha);
610*61046927SAndroid Build Coastguard Worker    } else {
611*61046927SAndroid Build Coastguard Worker       blend.rt[0].blend_enable = 0;
612*61046927SAndroid Build Coastguard Worker    }
613*61046927SAndroid Build Coastguard Worker 
614*61046927SAndroid Build Coastguard Worker    blend.logicop_enable = 0;
615*61046927SAndroid Build Coastguard Worker    blend.logicop_func = PIPE_LOGICOP_CLEAR;
616*61046927SAndroid Build Coastguard Worker    blend.rt[0].colormask = PIPE_MASK_RGBA;
617*61046927SAndroid Build Coastguard Worker    blend.dither = 0;
618*61046927SAndroid Build Coastguard Worker 
619*61046927SAndroid Build Coastguard Worker    return context->create_blend_state(context, &blend);
620*61046927SAndroid Build Coastguard Worker }
621*61046927SAndroid Build Coastguard Worker 
622*61046927SAndroid Build Coastguard Worker static struct vertex4f *
ColorsToPipe(VdpColor const * colors,uint32_t flags,struct vertex4f result[4])623*61046927SAndroid Build Coastguard Worker ColorsToPipe(VdpColor const *colors, uint32_t flags, struct vertex4f result[4])
624*61046927SAndroid Build Coastguard Worker {
625*61046927SAndroid Build Coastguard Worker    unsigned i;
626*61046927SAndroid Build Coastguard Worker    struct vertex4f *dst = result;
627*61046927SAndroid Build Coastguard Worker 
628*61046927SAndroid Build Coastguard Worker    if (!colors)
629*61046927SAndroid Build Coastguard Worker       return NULL;
630*61046927SAndroid Build Coastguard Worker 
631*61046927SAndroid Build Coastguard Worker    for (i = 0; i < 4; ++i) {
632*61046927SAndroid Build Coastguard Worker       dst->x = colors->red;
633*61046927SAndroid Build Coastguard Worker       dst->y = colors->green;
634*61046927SAndroid Build Coastguard Worker       dst->z = colors->blue;
635*61046927SAndroid Build Coastguard Worker       dst->w = colors->alpha;
636*61046927SAndroid Build Coastguard Worker 
637*61046927SAndroid Build Coastguard Worker       ++dst;
638*61046927SAndroid Build Coastguard Worker       if (flags & VDP_OUTPUT_SURFACE_RENDER_COLOR_PER_VERTEX)
639*61046927SAndroid Build Coastguard Worker          ++colors;
640*61046927SAndroid Build Coastguard Worker    }
641*61046927SAndroid Build Coastguard Worker    return result;
642*61046927SAndroid Build Coastguard Worker }
643*61046927SAndroid Build Coastguard Worker 
644*61046927SAndroid Build Coastguard Worker /**
645*61046927SAndroid Build Coastguard Worker  * Composite a sub-rectangle of a VdpOutputSurface into a sub-rectangle of
646*61046927SAndroid Build Coastguard Worker  * another VdpOutputSurface; Output Surface object VdpOutputSurface.
647*61046927SAndroid Build Coastguard Worker  */
648*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfaceRenderOutputSurface(VdpOutputSurface destination_surface,VdpRect const * destination_rect,VdpOutputSurface source_surface,VdpRect const * source_rect,VdpColor const * colors,VdpOutputSurfaceRenderBlendState const * blend_state,uint32_t flags)649*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfaceRenderOutputSurface(VdpOutputSurface destination_surface,
650*61046927SAndroid Build Coastguard Worker                                       VdpRect const *destination_rect,
651*61046927SAndroid Build Coastguard Worker                                       VdpOutputSurface source_surface,
652*61046927SAndroid Build Coastguard Worker                                       VdpRect const *source_rect,
653*61046927SAndroid Build Coastguard Worker                                       VdpColor const *colors,
654*61046927SAndroid Build Coastguard Worker                                       VdpOutputSurfaceRenderBlendState const *blend_state,
655*61046927SAndroid Build Coastguard Worker                                       uint32_t flags)
656*61046927SAndroid Build Coastguard Worker {
657*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *dst_vlsurface;
658*61046927SAndroid Build Coastguard Worker 
659*61046927SAndroid Build Coastguard Worker    struct pipe_context *context;
660*61046927SAndroid Build Coastguard Worker    struct pipe_sampler_view *src_sv;
661*61046927SAndroid Build Coastguard Worker    struct vl_compositor *compositor;
662*61046927SAndroid Build Coastguard Worker    struct vl_compositor_state *cstate;
663*61046927SAndroid Build Coastguard Worker 
664*61046927SAndroid Build Coastguard Worker    struct u_rect src_rect, dst_rect;
665*61046927SAndroid Build Coastguard Worker 
666*61046927SAndroid Build Coastguard Worker    struct vertex4f vlcolors[4];
667*61046927SAndroid Build Coastguard Worker    void *blend;
668*61046927SAndroid Build Coastguard Worker 
669*61046927SAndroid Build Coastguard Worker    dst_vlsurface = vlGetDataHTAB(destination_surface);
670*61046927SAndroid Build Coastguard Worker    if (!dst_vlsurface)
671*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
672*61046927SAndroid Build Coastguard Worker 
673*61046927SAndroid Build Coastguard Worker    if (source_surface == VDP_INVALID_HANDLE) {
674*61046927SAndroid Build Coastguard Worker       src_sv = dst_vlsurface->device->dummy_sv;
675*61046927SAndroid Build Coastguard Worker 
676*61046927SAndroid Build Coastguard Worker    } else {
677*61046927SAndroid Build Coastguard Worker       vlVdpOutputSurface *src_vlsurface = vlGetDataHTAB(source_surface);
678*61046927SAndroid Build Coastguard Worker       if (!src_vlsurface)
679*61046927SAndroid Build Coastguard Worker          return VDP_STATUS_INVALID_HANDLE;
680*61046927SAndroid Build Coastguard Worker 
681*61046927SAndroid Build Coastguard Worker       if (dst_vlsurface->device != src_vlsurface->device)
682*61046927SAndroid Build Coastguard Worker          return VDP_STATUS_HANDLE_DEVICE_MISMATCH;
683*61046927SAndroid Build Coastguard Worker 
684*61046927SAndroid Build Coastguard Worker       src_sv = src_vlsurface->sampler_view;
685*61046927SAndroid Build Coastguard Worker    }
686*61046927SAndroid Build Coastguard Worker 
687*61046927SAndroid Build Coastguard Worker    mtx_lock(&dst_vlsurface->device->mutex);
688*61046927SAndroid Build Coastguard Worker 
689*61046927SAndroid Build Coastguard Worker    context = dst_vlsurface->device->context;
690*61046927SAndroid Build Coastguard Worker    compositor = &dst_vlsurface->device->compositor;
691*61046927SAndroid Build Coastguard Worker    cstate = &dst_vlsurface->cstate;
692*61046927SAndroid Build Coastguard Worker 
693*61046927SAndroid Build Coastguard Worker    blend = BlenderToPipe(context, blend_state);
694*61046927SAndroid Build Coastguard Worker 
695*61046927SAndroid Build Coastguard Worker    vl_compositor_clear_layers(cstate);
696*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_blend(cstate, 0, blend, false);
697*61046927SAndroid Build Coastguard Worker    vl_compositor_set_rgba_layer(cstate, compositor, 0, src_sv,
698*61046927SAndroid Build Coastguard Worker                                 RectToPipe(source_rect, &src_rect), NULL,
699*61046927SAndroid Build Coastguard Worker                                 ColorsToPipe(colors, flags, vlcolors));
700*61046927SAndroid Build Coastguard Worker    STATIC_ASSERT(VL_COMPOSITOR_ROTATE_0 == VDP_OUTPUT_SURFACE_RENDER_ROTATE_0);
701*61046927SAndroid Build Coastguard Worker    STATIC_ASSERT(VL_COMPOSITOR_ROTATE_90 == VDP_OUTPUT_SURFACE_RENDER_ROTATE_90);
702*61046927SAndroid Build Coastguard Worker    STATIC_ASSERT(VL_COMPOSITOR_ROTATE_180 == VDP_OUTPUT_SURFACE_RENDER_ROTATE_180);
703*61046927SAndroid Build Coastguard Worker    STATIC_ASSERT(VL_COMPOSITOR_ROTATE_270 == VDP_OUTPUT_SURFACE_RENDER_ROTATE_270);
704*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_rotation(cstate, 0, flags & 3);
705*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_dst_area(cstate, 0, RectToPipe(destination_rect, &dst_rect));
706*61046927SAndroid Build Coastguard Worker    vl_compositor_render(cstate, compositor, dst_vlsurface->surface, &dst_vlsurface->dirty_area, false);
707*61046927SAndroid Build Coastguard Worker 
708*61046927SAndroid Build Coastguard Worker    context->delete_blend_state(context, blend);
709*61046927SAndroid Build Coastguard Worker    mtx_unlock(&dst_vlsurface->device->mutex);
710*61046927SAndroid Build Coastguard Worker 
711*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
712*61046927SAndroid Build Coastguard Worker }
713*61046927SAndroid Build Coastguard Worker 
714*61046927SAndroid Build Coastguard Worker /**
715*61046927SAndroid Build Coastguard Worker  * Composite a sub-rectangle of a VdpBitmapSurface into a sub-rectangle of
716*61046927SAndroid Build Coastguard Worker  * a VdpOutputSurface; Output Surface object VdpOutputSurface.
717*61046927SAndroid Build Coastguard Worker  */
718*61046927SAndroid Build Coastguard Worker VdpStatus
vlVdpOutputSurfaceRenderBitmapSurface(VdpOutputSurface destination_surface,VdpRect const * destination_rect,VdpBitmapSurface source_surface,VdpRect const * source_rect,VdpColor const * colors,VdpOutputSurfaceRenderBlendState const * blend_state,uint32_t flags)719*61046927SAndroid Build Coastguard Worker vlVdpOutputSurfaceRenderBitmapSurface(VdpOutputSurface destination_surface,
720*61046927SAndroid Build Coastguard Worker                                       VdpRect const *destination_rect,
721*61046927SAndroid Build Coastguard Worker                                       VdpBitmapSurface source_surface,
722*61046927SAndroid Build Coastguard Worker                                       VdpRect const *source_rect,
723*61046927SAndroid Build Coastguard Worker                                       VdpColor const *colors,
724*61046927SAndroid Build Coastguard Worker                                       VdpOutputSurfaceRenderBlendState const *blend_state,
725*61046927SAndroid Build Coastguard Worker                                       uint32_t flags)
726*61046927SAndroid Build Coastguard Worker {
727*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *dst_vlsurface;
728*61046927SAndroid Build Coastguard Worker 
729*61046927SAndroid Build Coastguard Worker    struct pipe_context *context;
730*61046927SAndroid Build Coastguard Worker    struct pipe_sampler_view *src_sv;
731*61046927SAndroid Build Coastguard Worker    struct vl_compositor *compositor;
732*61046927SAndroid Build Coastguard Worker    struct vl_compositor_state *cstate;
733*61046927SAndroid Build Coastguard Worker 
734*61046927SAndroid Build Coastguard Worker    struct u_rect src_rect, dst_rect;
735*61046927SAndroid Build Coastguard Worker 
736*61046927SAndroid Build Coastguard Worker    struct vertex4f vlcolors[4];
737*61046927SAndroid Build Coastguard Worker    void *blend;
738*61046927SAndroid Build Coastguard Worker 
739*61046927SAndroid Build Coastguard Worker    dst_vlsurface = vlGetDataHTAB(destination_surface);
740*61046927SAndroid Build Coastguard Worker    if (!dst_vlsurface)
741*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
742*61046927SAndroid Build Coastguard Worker 
743*61046927SAndroid Build Coastguard Worker    if (source_surface == VDP_INVALID_HANDLE) {
744*61046927SAndroid Build Coastguard Worker       src_sv = dst_vlsurface->device->dummy_sv;
745*61046927SAndroid Build Coastguard Worker 
746*61046927SAndroid Build Coastguard Worker    } else {
747*61046927SAndroid Build Coastguard Worker       vlVdpBitmapSurface *src_vlsurface = vlGetDataHTAB(source_surface);
748*61046927SAndroid Build Coastguard Worker       if (!src_vlsurface)
749*61046927SAndroid Build Coastguard Worker          return VDP_STATUS_INVALID_HANDLE;
750*61046927SAndroid Build Coastguard Worker 
751*61046927SAndroid Build Coastguard Worker       if (dst_vlsurface->device != src_vlsurface->device)
752*61046927SAndroid Build Coastguard Worker          return VDP_STATUS_HANDLE_DEVICE_MISMATCH;
753*61046927SAndroid Build Coastguard Worker 
754*61046927SAndroid Build Coastguard Worker       src_sv = src_vlsurface->sampler_view;
755*61046927SAndroid Build Coastguard Worker    }
756*61046927SAndroid Build Coastguard Worker 
757*61046927SAndroid Build Coastguard Worker    context = dst_vlsurface->device->context;
758*61046927SAndroid Build Coastguard Worker    compositor = &dst_vlsurface->device->compositor;
759*61046927SAndroid Build Coastguard Worker    cstate = &dst_vlsurface->cstate;
760*61046927SAndroid Build Coastguard Worker 
761*61046927SAndroid Build Coastguard Worker    mtx_lock(&dst_vlsurface->device->mutex);
762*61046927SAndroid Build Coastguard Worker 
763*61046927SAndroid Build Coastguard Worker    blend = BlenderToPipe(context, blend_state);
764*61046927SAndroid Build Coastguard Worker 
765*61046927SAndroid Build Coastguard Worker    vl_compositor_clear_layers(cstate);
766*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_blend(cstate, 0, blend, false);
767*61046927SAndroid Build Coastguard Worker    vl_compositor_set_rgba_layer(cstate, compositor, 0, src_sv,
768*61046927SAndroid Build Coastguard Worker                                 RectToPipe(source_rect, &src_rect), NULL,
769*61046927SAndroid Build Coastguard Worker                                 ColorsToPipe(colors, flags, vlcolors));
770*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_rotation(cstate, 0, flags & 3);
771*61046927SAndroid Build Coastguard Worker    vl_compositor_set_layer_dst_area(cstate, 0, RectToPipe(destination_rect, &dst_rect));
772*61046927SAndroid Build Coastguard Worker    vl_compositor_render(cstate, compositor, dst_vlsurface->surface, &dst_vlsurface->dirty_area, false);
773*61046927SAndroid Build Coastguard Worker 
774*61046927SAndroid Build Coastguard Worker    context->delete_blend_state(context, blend);
775*61046927SAndroid Build Coastguard Worker    mtx_unlock(&dst_vlsurface->device->mutex);
776*61046927SAndroid Build Coastguard Worker 
777*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
778*61046927SAndroid Build Coastguard Worker }
779*61046927SAndroid Build Coastguard Worker 
vlVdpOutputSurfaceGallium(VdpOutputSurface surface)780*61046927SAndroid Build Coastguard Worker struct pipe_resource *vlVdpOutputSurfaceGallium(VdpOutputSurface surface)
781*61046927SAndroid Build Coastguard Worker {
782*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
783*61046927SAndroid Build Coastguard Worker 
784*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
785*61046927SAndroid Build Coastguard Worker    if (!vlsurface || !vlsurface->surface)
786*61046927SAndroid Build Coastguard Worker       return NULL;
787*61046927SAndroid Build Coastguard Worker 
788*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
789*61046927SAndroid Build Coastguard Worker    vlsurface->device->context->flush(vlsurface->device->context, NULL, 0);
790*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
791*61046927SAndroid Build Coastguard Worker 
792*61046927SAndroid Build Coastguard Worker    return vlsurface->surface->texture;
793*61046927SAndroid Build Coastguard Worker }
794*61046927SAndroid Build Coastguard Worker 
vlVdpOutputSurfaceDMABuf(VdpOutputSurface surface,struct VdpSurfaceDMABufDesc * result)795*61046927SAndroid Build Coastguard Worker VdpStatus vlVdpOutputSurfaceDMABuf(VdpOutputSurface surface,
796*61046927SAndroid Build Coastguard Worker                                    struct VdpSurfaceDMABufDesc *result)
797*61046927SAndroid Build Coastguard Worker {
798*61046927SAndroid Build Coastguard Worker    vlVdpOutputSurface *vlsurface;
799*61046927SAndroid Build Coastguard Worker    struct pipe_screen *pscreen;
800*61046927SAndroid Build Coastguard Worker    struct winsys_handle whandle;
801*61046927SAndroid Build Coastguard Worker 
802*61046927SAndroid Build Coastguard Worker    memset(result, 0, sizeof(*result));
803*61046927SAndroid Build Coastguard Worker    result->handle = -1;
804*61046927SAndroid Build Coastguard Worker 
805*61046927SAndroid Build Coastguard Worker    vlsurface = vlGetDataHTAB(surface);
806*61046927SAndroid Build Coastguard Worker    if (!vlsurface || !vlsurface->surface)
807*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_INVALID_HANDLE;
808*61046927SAndroid Build Coastguard Worker 
809*61046927SAndroid Build Coastguard Worker    mtx_lock(&vlsurface->device->mutex);
810*61046927SAndroid Build Coastguard Worker    vlsurface->device->context->flush(vlsurface->device->context, NULL, 0);
811*61046927SAndroid Build Coastguard Worker 
812*61046927SAndroid Build Coastguard Worker    memset(&whandle, 0, sizeof(struct winsys_handle));
813*61046927SAndroid Build Coastguard Worker    whandle.type = WINSYS_HANDLE_TYPE_FD;
814*61046927SAndroid Build Coastguard Worker 
815*61046927SAndroid Build Coastguard Worker    pscreen = vlsurface->surface->texture->screen;
816*61046927SAndroid Build Coastguard Worker    if (!pscreen->resource_get_handle(pscreen, vlsurface->device->context,
817*61046927SAndroid Build Coastguard Worker                                      vlsurface->surface->texture, &whandle,
818*61046927SAndroid Build Coastguard Worker                                      PIPE_HANDLE_USAGE_FRAMEBUFFER_WRITE)) {
819*61046927SAndroid Build Coastguard Worker       mtx_unlock(&vlsurface->device->mutex);
820*61046927SAndroid Build Coastguard Worker       return VDP_STATUS_NO_IMPLEMENTATION;
821*61046927SAndroid Build Coastguard Worker    }
822*61046927SAndroid Build Coastguard Worker 
823*61046927SAndroid Build Coastguard Worker    mtx_unlock(&vlsurface->device->mutex);
824*61046927SAndroid Build Coastguard Worker 
825*61046927SAndroid Build Coastguard Worker    result->handle = whandle.handle;
826*61046927SAndroid Build Coastguard Worker    result->width = vlsurface->surface->width;
827*61046927SAndroid Build Coastguard Worker    result->height = vlsurface->surface->height;
828*61046927SAndroid Build Coastguard Worker    result->offset = whandle.offset;
829*61046927SAndroid Build Coastguard Worker    result->stride = whandle.stride;
830*61046927SAndroid Build Coastguard Worker    result->format = PipeToFormatRGBA(vlsurface->surface->format);
831*61046927SAndroid Build Coastguard Worker 
832*61046927SAndroid Build Coastguard Worker    return VDP_STATUS_OK;
833*61046927SAndroid Build Coastguard Worker }
834