1bf215546Sopenharmony_ci/*
2bf215546Sopenharmony_ci * Copyright © 2011 Intel Corporation
3bf215546Sopenharmony_ci *
4bf215546Sopenharmony_ci * Permission is hereby granted, free of charge, to any person obtaining a
5bf215546Sopenharmony_ci * copy of this software and associated documentation files (the "Software"),
6bf215546Sopenharmony_ci * to deal in the Software without restriction, including without limitation
7bf215546Sopenharmony_ci * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8bf215546Sopenharmony_ci * and/or sell copies of the Software, and to permit persons to whom the
9bf215546Sopenharmony_ci * Software is furnished to do so, subject to the following conditions:
10bf215546Sopenharmony_ci *
11bf215546Sopenharmony_ci * The above copyright notice and this permission notice (including the next
12bf215546Sopenharmony_ci * paragraph) shall be included in all copies or substantial portions of the
13bf215546Sopenharmony_ci * Software.
14bf215546Sopenharmony_ci *
15bf215546Sopenharmony_ci * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16bf215546Sopenharmony_ci * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17bf215546Sopenharmony_ci * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18bf215546Sopenharmony_ci * NONINFRINGEMENT.  IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
19bf215546Sopenharmony_ci * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20bf215546Sopenharmony_ci * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21bf215546Sopenharmony_ci * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22bf215546Sopenharmony_ci * DEALINGS IN THE SOFTWARE.
23bf215546Sopenharmony_ci *
24bf215546Sopenharmony_ci * Authors:
25bf215546Sopenharmony_ci *    Benjamin Franzke <benjaminfranzke@googlemail.com>
26bf215546Sopenharmony_ci */
27bf215546Sopenharmony_ci
28bf215546Sopenharmony_ci#include <stddef.h>
29bf215546Sopenharmony_ci#include <stdio.h>
30bf215546Sopenharmony_ci#include <stdlib.h>
31bf215546Sopenharmony_ci#include <string.h>
32bf215546Sopenharmony_ci#include <stdint.h>
33bf215546Sopenharmony_ci
34bf215546Sopenharmony_ci#ifdef MAJOR_IN_MKDEV
35bf215546Sopenharmony_ci#include <sys/mkdev.h>
36bf215546Sopenharmony_ci#endif
37bf215546Sopenharmony_ci#ifdef MAJOR_IN_SYSMACROS
38bf215546Sopenharmony_ci#include <sys/sysmacros.h>
39bf215546Sopenharmony_ci#endif
40bf215546Sopenharmony_ci#include <sys/stat.h>
41bf215546Sopenharmony_ci#include <unistd.h>
42bf215546Sopenharmony_ci#include <errno.h>
43bf215546Sopenharmony_ci
44bf215546Sopenharmony_ci#include "gbm.h"
45bf215546Sopenharmony_ci#include "gbmint.h"
46bf215546Sopenharmony_ci#include "backend.h"
47bf215546Sopenharmony_ci
48bf215546Sopenharmony_ci/** Returns the file description for the gbm device
49bf215546Sopenharmony_ci *
50bf215546Sopenharmony_ci * \return The fd that the struct gbm_device was created with
51bf215546Sopenharmony_ci */
52bf215546Sopenharmony_ciGBM_EXPORT int
53bf215546Sopenharmony_cigbm_device_get_fd(struct gbm_device *gbm)
54bf215546Sopenharmony_ci{
55bf215546Sopenharmony_ci   return gbm->v0.fd;
56bf215546Sopenharmony_ci}
57bf215546Sopenharmony_ci
58bf215546Sopenharmony_ci/** Get the backend name for the given gbm device
59bf215546Sopenharmony_ci *
60bf215546Sopenharmony_ci * \return The backend name string - this belongs to the device and must not
61bf215546Sopenharmony_ci * be freed
62bf215546Sopenharmony_ci */
63bf215546Sopenharmony_ciGBM_EXPORT const char *
64bf215546Sopenharmony_cigbm_device_get_backend_name(struct gbm_device *gbm)
65bf215546Sopenharmony_ci{
66bf215546Sopenharmony_ci   return gbm->v0.name;
67bf215546Sopenharmony_ci}
68bf215546Sopenharmony_ci
69bf215546Sopenharmony_ci/** Test if a format is supported for a given set of usage flags.
70bf215546Sopenharmony_ci *
71bf215546Sopenharmony_ci * \param gbm The created buffer manager
72bf215546Sopenharmony_ci * \param format The format to test
73bf215546Sopenharmony_ci * \param flags A bitmask of the usages to test the format against
74bf215546Sopenharmony_ci * \return 1 if the format is supported otherwise 0
75bf215546Sopenharmony_ci *
76bf215546Sopenharmony_ci * \sa enum gbm_bo_flags for the list of flags that the format can be
77bf215546Sopenharmony_ci * tested against
78bf215546Sopenharmony_ci *
79bf215546Sopenharmony_ci * \sa enum gbm_bo_format for the list of formats
80bf215546Sopenharmony_ci */
81bf215546Sopenharmony_ciGBM_EXPORT int
82bf215546Sopenharmony_cigbm_device_is_format_supported(struct gbm_device *gbm,
83bf215546Sopenharmony_ci                               uint32_t format, uint32_t flags)
84bf215546Sopenharmony_ci{
85bf215546Sopenharmony_ci   return gbm->v0.is_format_supported(gbm, format, flags);
86bf215546Sopenharmony_ci}
87bf215546Sopenharmony_ci
88bf215546Sopenharmony_ci/** Get the number of planes that are required for a given format+modifier
89bf215546Sopenharmony_ci *
90bf215546Sopenharmony_ci * \param gbm The gbm device returned from gbm_create_device()
91bf215546Sopenharmony_ci * \param format The format to query
92bf215546Sopenharmony_ci * \param modifier The modifier to query
93bf215546Sopenharmony_ci */
94bf215546Sopenharmony_ciGBM_EXPORT int
95bf215546Sopenharmony_cigbm_device_get_format_modifier_plane_count(struct gbm_device *gbm,
96bf215546Sopenharmony_ci                                           uint32_t format,
97bf215546Sopenharmony_ci                                           uint64_t modifier)
98bf215546Sopenharmony_ci{
99bf215546Sopenharmony_ci   return gbm->v0.get_format_modifier_plane_count(gbm, format, modifier);
100bf215546Sopenharmony_ci}
101bf215546Sopenharmony_ci
102bf215546Sopenharmony_ci/** Destroy the gbm device and free all resources associated with it.
103bf215546Sopenharmony_ci *
104bf215546Sopenharmony_ci * Prior to calling this function all buffers and surfaces created with the
105bf215546Sopenharmony_ci * gbm device need to be destroyed.
106bf215546Sopenharmony_ci *
107bf215546Sopenharmony_ci * \param gbm The device created using gbm_create_device()
108bf215546Sopenharmony_ci */
109bf215546Sopenharmony_ciGBM_EXPORT void
110bf215546Sopenharmony_cigbm_device_destroy(struct gbm_device *gbm)
111bf215546Sopenharmony_ci{
112bf215546Sopenharmony_ci   _gbm_device_destroy(gbm);
113bf215546Sopenharmony_ci}
114bf215546Sopenharmony_ci
115bf215546Sopenharmony_ci/** Create a gbm device for allocating buffers
116bf215546Sopenharmony_ci *
117bf215546Sopenharmony_ci * The file descriptor passed in is used by the backend to communicate with
118bf215546Sopenharmony_ci * platform for allocating the memory. For allocations using DRI this would be
119bf215546Sopenharmony_ci * the file descriptor returned when opening a device such as \c
120bf215546Sopenharmony_ci * /dev/dri/card0
121bf215546Sopenharmony_ci *
122bf215546Sopenharmony_ci * \param fd The file descriptor for a backend specific device
123bf215546Sopenharmony_ci * \return The newly created struct gbm_device. The resources associated with
124bf215546Sopenharmony_ci * the device should be freed with gbm_device_destroy() when it is no longer
125bf215546Sopenharmony_ci * needed. If the creation of the device failed NULL will be returned.
126bf215546Sopenharmony_ci */
127bf215546Sopenharmony_ciGBM_EXPORT struct gbm_device *
128bf215546Sopenharmony_cigbm_create_device(int fd)
129bf215546Sopenharmony_ci{
130bf215546Sopenharmony_ci   struct gbm_device *gbm = NULL;
131bf215546Sopenharmony_ci   struct stat buf;
132bf215546Sopenharmony_ci
133bf215546Sopenharmony_ci   if (fd < 0 || fstat(fd, &buf) < 0 || !S_ISCHR(buf.st_mode)) {
134bf215546Sopenharmony_ci      errno = EINVAL;
135bf215546Sopenharmony_ci      return NULL;
136bf215546Sopenharmony_ci   }
137bf215546Sopenharmony_ci
138bf215546Sopenharmony_ci   gbm = _gbm_create_device(fd);
139bf215546Sopenharmony_ci   if (gbm == NULL)
140bf215546Sopenharmony_ci      return NULL;
141bf215546Sopenharmony_ci
142bf215546Sopenharmony_ci   gbm->dummy = gbm_create_device;
143bf215546Sopenharmony_ci
144bf215546Sopenharmony_ci   return gbm;
145bf215546Sopenharmony_ci}
146bf215546Sopenharmony_ci
147bf215546Sopenharmony_ci/** Get the width of the buffer object
148bf215546Sopenharmony_ci *
149bf215546Sopenharmony_ci * \param bo The buffer object
150bf215546Sopenharmony_ci * \return The width of the allocated buffer object
151bf215546Sopenharmony_ci *
152bf215546Sopenharmony_ci */
153bf215546Sopenharmony_ciGBM_EXPORT uint32_t
154bf215546Sopenharmony_cigbm_bo_get_width(struct gbm_bo *bo)
155bf215546Sopenharmony_ci{
156bf215546Sopenharmony_ci   return bo->v0.width;
157bf215546Sopenharmony_ci}
158bf215546Sopenharmony_ci
159bf215546Sopenharmony_ci/** Get the height of the buffer object
160bf215546Sopenharmony_ci *
161bf215546Sopenharmony_ci * \param bo The buffer object
162bf215546Sopenharmony_ci * \return The height of the allocated buffer object
163bf215546Sopenharmony_ci */
164bf215546Sopenharmony_ciGBM_EXPORT uint32_t
165bf215546Sopenharmony_cigbm_bo_get_height(struct gbm_bo *bo)
166bf215546Sopenharmony_ci{
167bf215546Sopenharmony_ci   return bo->v0.height;
168bf215546Sopenharmony_ci}
169bf215546Sopenharmony_ci
170bf215546Sopenharmony_ci/** Get the stride of the buffer object
171bf215546Sopenharmony_ci *
172bf215546Sopenharmony_ci * This is calculated by the backend when it does the allocation in
173bf215546Sopenharmony_ci * gbm_bo_create()
174bf215546Sopenharmony_ci *
175bf215546Sopenharmony_ci * \param bo The buffer object
176bf215546Sopenharmony_ci * \return The stride of the allocated buffer object in bytes
177bf215546Sopenharmony_ci */
178bf215546Sopenharmony_ciGBM_EXPORT uint32_t
179bf215546Sopenharmony_cigbm_bo_get_stride(struct gbm_bo *bo)
180bf215546Sopenharmony_ci{
181bf215546Sopenharmony_ci   return gbm_bo_get_stride_for_plane(bo, 0);
182bf215546Sopenharmony_ci}
183bf215546Sopenharmony_ci
184bf215546Sopenharmony_ci/** Get the stride for the given plane
185bf215546Sopenharmony_ci *
186bf215546Sopenharmony_ci * \param bo The buffer object
187bf215546Sopenharmony_ci * \param plane for which you want the stride
188bf215546Sopenharmony_ci *
189bf215546Sopenharmony_ci * \sa gbm_bo_get_stride()
190bf215546Sopenharmony_ci */
191bf215546Sopenharmony_ciGBM_EXPORT uint32_t
192bf215546Sopenharmony_cigbm_bo_get_stride_for_plane(struct gbm_bo *bo, int plane)
193bf215546Sopenharmony_ci{
194bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_stride(bo, plane);
195bf215546Sopenharmony_ci}
196bf215546Sopenharmony_ci
197bf215546Sopenharmony_ci/** Get the format of the buffer object
198bf215546Sopenharmony_ci *
199bf215546Sopenharmony_ci * The format of the pixels in the buffer.
200bf215546Sopenharmony_ci *
201bf215546Sopenharmony_ci * \param bo The buffer object
202bf215546Sopenharmony_ci * \return The format of buffer object, one of the GBM_FORMAT_* codes
203bf215546Sopenharmony_ci */
204bf215546Sopenharmony_ciGBM_EXPORT uint32_t
205bf215546Sopenharmony_cigbm_bo_get_format(struct gbm_bo *bo)
206bf215546Sopenharmony_ci{
207bf215546Sopenharmony_ci   return bo->v0.format;
208bf215546Sopenharmony_ci}
209bf215546Sopenharmony_ci
210bf215546Sopenharmony_ci/** Get the bit-per-pixel of the buffer object's format
211bf215546Sopenharmony_ci *
212bf215546Sopenharmony_ci * The bits-per-pixel of the buffer object's format.
213bf215546Sopenharmony_ci *
214bf215546Sopenharmony_ci * Note; The 'in-memory pixel' concept makes no sense for YUV formats
215bf215546Sopenharmony_ci * (pixels are the result of the combination of multiple memory sources:
216bf215546Sopenharmony_ci * Y, Cb & Cr; usually these are even in separate buffers), so YUV
217bf215546Sopenharmony_ci * formats are not supported by this function.
218bf215546Sopenharmony_ci *
219bf215546Sopenharmony_ci * \param bo The buffer object
220bf215546Sopenharmony_ci * \return The number of bits0per-pixel of the buffer object's format.
221bf215546Sopenharmony_ci */
222bf215546Sopenharmony_ciGBM_EXPORT uint32_t
223bf215546Sopenharmony_cigbm_bo_get_bpp(struct gbm_bo *bo)
224bf215546Sopenharmony_ci{
225bf215546Sopenharmony_ci   switch (bo->v0.format) {
226bf215546Sopenharmony_ci      default:
227bf215546Sopenharmony_ci         return 0;
228bf215546Sopenharmony_ci      case GBM_FORMAT_C8:
229bf215546Sopenharmony_ci      case GBM_FORMAT_R8:
230bf215546Sopenharmony_ci      case GBM_FORMAT_RGB332:
231bf215546Sopenharmony_ci      case GBM_FORMAT_BGR233:
232bf215546Sopenharmony_ci         return 8;
233bf215546Sopenharmony_ci      case GBM_FORMAT_R16:
234bf215546Sopenharmony_ci      case GBM_FORMAT_GR88:
235bf215546Sopenharmony_ci      case GBM_FORMAT_XRGB4444:
236bf215546Sopenharmony_ci      case GBM_FORMAT_XBGR4444:
237bf215546Sopenharmony_ci      case GBM_FORMAT_RGBX4444:
238bf215546Sopenharmony_ci      case GBM_FORMAT_BGRX4444:
239bf215546Sopenharmony_ci      case GBM_FORMAT_ARGB4444:
240bf215546Sopenharmony_ci      case GBM_FORMAT_ABGR4444:
241bf215546Sopenharmony_ci      case GBM_FORMAT_RGBA4444:
242bf215546Sopenharmony_ci      case GBM_FORMAT_BGRA4444:
243bf215546Sopenharmony_ci      case GBM_FORMAT_XRGB1555:
244bf215546Sopenharmony_ci      case GBM_FORMAT_XBGR1555:
245bf215546Sopenharmony_ci      case GBM_FORMAT_RGBX5551:
246bf215546Sopenharmony_ci      case GBM_FORMAT_BGRX5551:
247bf215546Sopenharmony_ci      case GBM_FORMAT_ARGB1555:
248bf215546Sopenharmony_ci      case GBM_FORMAT_ABGR1555:
249bf215546Sopenharmony_ci      case GBM_FORMAT_RGBA5551:
250bf215546Sopenharmony_ci      case GBM_FORMAT_BGRA5551:
251bf215546Sopenharmony_ci      case GBM_FORMAT_RGB565:
252bf215546Sopenharmony_ci      case GBM_FORMAT_BGR565:
253bf215546Sopenharmony_ci         return 16;
254bf215546Sopenharmony_ci      case GBM_FORMAT_RGB888:
255bf215546Sopenharmony_ci      case GBM_FORMAT_BGR888:
256bf215546Sopenharmony_ci         return 24;
257bf215546Sopenharmony_ci      case GBM_FORMAT_RG1616:
258bf215546Sopenharmony_ci      case GBM_FORMAT_GR1616:
259bf215546Sopenharmony_ci      case GBM_FORMAT_XRGB8888:
260bf215546Sopenharmony_ci      case GBM_FORMAT_XBGR8888:
261bf215546Sopenharmony_ci      case GBM_FORMAT_RGBX8888:
262bf215546Sopenharmony_ci      case GBM_FORMAT_BGRX8888:
263bf215546Sopenharmony_ci      case GBM_FORMAT_ARGB8888:
264bf215546Sopenharmony_ci      case GBM_FORMAT_ABGR8888:
265bf215546Sopenharmony_ci      case GBM_FORMAT_RGBA8888:
266bf215546Sopenharmony_ci      case GBM_FORMAT_BGRA8888:
267bf215546Sopenharmony_ci      case GBM_FORMAT_XRGB2101010:
268bf215546Sopenharmony_ci      case GBM_FORMAT_XBGR2101010:
269bf215546Sopenharmony_ci      case GBM_FORMAT_RGBX1010102:
270bf215546Sopenharmony_ci      case GBM_FORMAT_BGRX1010102:
271bf215546Sopenharmony_ci      case GBM_FORMAT_ARGB2101010:
272bf215546Sopenharmony_ci      case GBM_FORMAT_ABGR2101010:
273bf215546Sopenharmony_ci      case GBM_FORMAT_RGBA1010102:
274bf215546Sopenharmony_ci      case GBM_FORMAT_BGRA1010102:
275bf215546Sopenharmony_ci         return 32;
276bf215546Sopenharmony_ci      case GBM_FORMAT_XBGR16161616:
277bf215546Sopenharmony_ci      case GBM_FORMAT_ABGR16161616:
278bf215546Sopenharmony_ci      case GBM_FORMAT_XBGR16161616F:
279bf215546Sopenharmony_ci      case GBM_FORMAT_ABGR16161616F:
280bf215546Sopenharmony_ci         return 64;
281bf215546Sopenharmony_ci   }
282bf215546Sopenharmony_ci}
283bf215546Sopenharmony_ci
284bf215546Sopenharmony_ci/** Get the offset for the data of the specified plane
285bf215546Sopenharmony_ci *
286bf215546Sopenharmony_ci * Extra planes, and even the first plane, may have an offset from the start of
287bf215546Sopenharmony_ci * the buffer object. This function will provide the offset for the given plane
288bf215546Sopenharmony_ci * to be used in various KMS APIs.
289bf215546Sopenharmony_ci *
290bf215546Sopenharmony_ci * \param bo The buffer object
291bf215546Sopenharmony_ci * \return The offset
292bf215546Sopenharmony_ci */
293bf215546Sopenharmony_ciGBM_EXPORT uint32_t
294bf215546Sopenharmony_cigbm_bo_get_offset(struct gbm_bo *bo, int plane)
295bf215546Sopenharmony_ci{
296bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_offset(bo, plane);
297bf215546Sopenharmony_ci}
298bf215546Sopenharmony_ci
299bf215546Sopenharmony_ci/** Get the gbm device used to create the buffer object
300bf215546Sopenharmony_ci *
301bf215546Sopenharmony_ci * \param bo The buffer object
302bf215546Sopenharmony_ci * \return Returns the gbm device with which the buffer object was created
303bf215546Sopenharmony_ci */
304bf215546Sopenharmony_ciGBM_EXPORT struct gbm_device *
305bf215546Sopenharmony_cigbm_bo_get_device(struct gbm_bo *bo)
306bf215546Sopenharmony_ci{
307bf215546Sopenharmony_ci	return bo->gbm;
308bf215546Sopenharmony_ci}
309bf215546Sopenharmony_ci
310bf215546Sopenharmony_ci/** Get the handle of the buffer object
311bf215546Sopenharmony_ci *
312bf215546Sopenharmony_ci * This is stored in the platform generic union gbm_bo_handle type. However
313bf215546Sopenharmony_ci * the format of this handle is platform specific.
314bf215546Sopenharmony_ci *
315bf215546Sopenharmony_ci * \param bo The buffer object
316bf215546Sopenharmony_ci * \return Returns the handle of the allocated buffer object
317bf215546Sopenharmony_ci */
318bf215546Sopenharmony_ciGBM_EXPORT union gbm_bo_handle
319bf215546Sopenharmony_cigbm_bo_get_handle(struct gbm_bo *bo)
320bf215546Sopenharmony_ci{
321bf215546Sopenharmony_ci   return bo->v0.handle;
322bf215546Sopenharmony_ci}
323bf215546Sopenharmony_ci
324bf215546Sopenharmony_ci/** Get a DMA-BUF file descriptor for the buffer object
325bf215546Sopenharmony_ci *
326bf215546Sopenharmony_ci * This function creates a DMA-BUF (also known as PRIME) file descriptor
327bf215546Sopenharmony_ci * handle for the buffer object.  Each call to gbm_bo_get_fd() returns a new
328bf215546Sopenharmony_ci * file descriptor and the caller is responsible for closing the file
329bf215546Sopenharmony_ci * descriptor.
330bf215546Sopenharmony_ci
331bf215546Sopenharmony_ci * \param bo The buffer object
332bf215546Sopenharmony_ci * \return Returns a file descriptor referring to the underlying buffer or -1
333bf215546Sopenharmony_ci * if an error occurs.
334bf215546Sopenharmony_ci */
335bf215546Sopenharmony_ciGBM_EXPORT int
336bf215546Sopenharmony_cigbm_bo_get_fd(struct gbm_bo *bo)
337bf215546Sopenharmony_ci{
338bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_fd(bo);
339bf215546Sopenharmony_ci}
340bf215546Sopenharmony_ci
341bf215546Sopenharmony_ci/** Get the number of planes for the given bo.
342bf215546Sopenharmony_ci *
343bf215546Sopenharmony_ci * \param bo The buffer object
344bf215546Sopenharmony_ci * \return The number of planes
345bf215546Sopenharmony_ci */
346bf215546Sopenharmony_ciGBM_EXPORT int
347bf215546Sopenharmony_cigbm_bo_get_plane_count(struct gbm_bo *bo)
348bf215546Sopenharmony_ci{
349bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_planes(bo);
350bf215546Sopenharmony_ci}
351bf215546Sopenharmony_ci
352bf215546Sopenharmony_ci/** Get the handle for the specified plane of the buffer object
353bf215546Sopenharmony_ci *
354bf215546Sopenharmony_ci * This function gets the handle for any plane associated with the BO. When
355bf215546Sopenharmony_ci * dealing with multi-planar formats, or formats which might have implicit
356bf215546Sopenharmony_ci * planes based on different underlying hardware it is necessary for the client
357bf215546Sopenharmony_ci * to be able to get this information to pass to the DRM.
358bf215546Sopenharmony_ci *
359bf215546Sopenharmony_ci * \param bo The buffer object
360bf215546Sopenharmony_ci * \param plane the plane to get a handle for
361bf215546Sopenharmony_ci *
362bf215546Sopenharmony_ci * \sa gbm_bo_get_handle()
363bf215546Sopenharmony_ci */
364bf215546Sopenharmony_ciGBM_EXPORT union gbm_bo_handle
365bf215546Sopenharmony_cigbm_bo_get_handle_for_plane(struct gbm_bo *bo, int plane)
366bf215546Sopenharmony_ci{
367bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_handle(bo, plane);
368bf215546Sopenharmony_ci}
369bf215546Sopenharmony_ci
370bf215546Sopenharmony_ci/** Get a DMA-BUF file descriptor for the specified plane of the buffer object
371bf215546Sopenharmony_ci *
372bf215546Sopenharmony_ci * This function creates a DMA-BUF (also known as PRIME) file descriptor
373bf215546Sopenharmony_ci * handle for the specified plane of the buffer object.  Each call to
374bf215546Sopenharmony_ci * gbm_bo_get_fd_for_plane() returns a new file descriptor and the caller is
375bf215546Sopenharmony_ci * responsible for closing the file descriptor.
376bf215546Sopenharmony_ci
377bf215546Sopenharmony_ci * \param bo The buffer object
378bf215546Sopenharmony_ci * \param plane The plane to get a DMA-BUF for
379bf215546Sopenharmony_ci * \return Returns a file descriptor referring to the underlying buffer or -1
380bf215546Sopenharmony_ci * if an error occurs.
381bf215546Sopenharmony_ci *
382bf215546Sopenharmony_ci * \sa gbm_bo_get_fd()
383bf215546Sopenharmony_ci */
384bf215546Sopenharmony_ciGBM_EXPORT int
385bf215546Sopenharmony_cigbm_bo_get_fd_for_plane(struct gbm_bo *bo, int plane)
386bf215546Sopenharmony_ci{
387bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_plane_fd(bo, plane);
388bf215546Sopenharmony_ci}
389bf215546Sopenharmony_ci
390bf215546Sopenharmony_ci/**
391bf215546Sopenharmony_ci * Get the chosen modifier for the buffer object
392bf215546Sopenharmony_ci *
393bf215546Sopenharmony_ci * This function returns the modifier that was chosen for the object. These
394bf215546Sopenharmony_ci * properties may be generic, or platform/implementation dependent.
395bf215546Sopenharmony_ci *
396bf215546Sopenharmony_ci * \param bo The buffer object
397bf215546Sopenharmony_ci * \return Returns the selected modifier (chosen by the implementation) for the
398bf215546Sopenharmony_ci * BO.
399bf215546Sopenharmony_ci * \sa gbm_bo_create_with_modifiers() where possible modifiers are set
400bf215546Sopenharmony_ci * \sa gbm_surface_create_with_modifiers() where possible modifiers are set
401bf215546Sopenharmony_ci * \sa define DRM_FORMAT_MOD_* in drm_fourcc.h for possible modifiers
402bf215546Sopenharmony_ci */
403bf215546Sopenharmony_ciGBM_EXPORT uint64_t
404bf215546Sopenharmony_cigbm_bo_get_modifier(struct gbm_bo *bo)
405bf215546Sopenharmony_ci{
406bf215546Sopenharmony_ci   return bo->gbm->v0.bo_get_modifier(bo);
407bf215546Sopenharmony_ci}
408bf215546Sopenharmony_ci
409bf215546Sopenharmony_ci/** Write data into the buffer object
410bf215546Sopenharmony_ci *
411bf215546Sopenharmony_ci * If the buffer object was created with the GBM_BO_USE_WRITE flag,
412bf215546Sopenharmony_ci * this function can be used to write data into the buffer object.  The
413bf215546Sopenharmony_ci * data is copied directly into the object and it's the responsibility
414bf215546Sopenharmony_ci * of the caller to make sure the data represents valid pixel data,
415bf215546Sopenharmony_ci * according to the width, height, stride and format of the buffer object.
416bf215546Sopenharmony_ci *
417bf215546Sopenharmony_ci * \param bo The buffer object
418bf215546Sopenharmony_ci * \param buf The data to write
419bf215546Sopenharmony_ci * \param count The number of bytes to write
420bf215546Sopenharmony_ci * \return Returns 0 on success, otherwise -1 is returned an errno set
421bf215546Sopenharmony_ci */
422bf215546Sopenharmony_ciGBM_EXPORT int
423bf215546Sopenharmony_cigbm_bo_write(struct gbm_bo *bo, const void *buf, size_t count)
424bf215546Sopenharmony_ci{
425bf215546Sopenharmony_ci   return bo->gbm->v0.bo_write(bo, buf, count);
426bf215546Sopenharmony_ci}
427bf215546Sopenharmony_ci
428bf215546Sopenharmony_ci/** Set the user data associated with a buffer object
429bf215546Sopenharmony_ci *
430bf215546Sopenharmony_ci * \param bo The buffer object
431bf215546Sopenharmony_ci * \param data The data to associate to the buffer object
432bf215546Sopenharmony_ci * \param destroy_user_data A callback (which may be %NULL) that will be
433bf215546Sopenharmony_ci * called prior to the buffer destruction
434bf215546Sopenharmony_ci */
435bf215546Sopenharmony_ciGBM_EXPORT void
436bf215546Sopenharmony_cigbm_bo_set_user_data(struct gbm_bo *bo, void *data,
437bf215546Sopenharmony_ci		     void (*destroy_user_data)(struct gbm_bo *, void *))
438bf215546Sopenharmony_ci{
439bf215546Sopenharmony_ci   bo->v0.user_data = data;
440bf215546Sopenharmony_ci   bo->v0.destroy_user_data = destroy_user_data;
441bf215546Sopenharmony_ci}
442bf215546Sopenharmony_ci
443bf215546Sopenharmony_ci/** Get the user data associated with a buffer object
444bf215546Sopenharmony_ci *
445bf215546Sopenharmony_ci * \param bo The buffer object
446bf215546Sopenharmony_ci * \return Returns the user data associated with the buffer object or %NULL
447bf215546Sopenharmony_ci * if no data was associated with it
448bf215546Sopenharmony_ci *
449bf215546Sopenharmony_ci * \sa gbm_bo_set_user_data()
450bf215546Sopenharmony_ci */
451bf215546Sopenharmony_ciGBM_EXPORT void *
452bf215546Sopenharmony_cigbm_bo_get_user_data(struct gbm_bo *bo)
453bf215546Sopenharmony_ci{
454bf215546Sopenharmony_ci   return bo->v0.user_data;
455bf215546Sopenharmony_ci}
456bf215546Sopenharmony_ci
457bf215546Sopenharmony_ci/**
458bf215546Sopenharmony_ci * Destroys the given buffer object and frees all resources associated with
459bf215546Sopenharmony_ci * it.
460bf215546Sopenharmony_ci *
461bf215546Sopenharmony_ci * \param bo The buffer object
462bf215546Sopenharmony_ci */
463bf215546Sopenharmony_ciGBM_EXPORT void
464bf215546Sopenharmony_cigbm_bo_destroy(struct gbm_bo *bo)
465bf215546Sopenharmony_ci{
466bf215546Sopenharmony_ci   if (bo->v0.destroy_user_data)
467bf215546Sopenharmony_ci      bo->v0.destroy_user_data(bo, bo->v0.user_data);
468bf215546Sopenharmony_ci
469bf215546Sopenharmony_ci   bo->gbm->v0.bo_destroy(bo);
470bf215546Sopenharmony_ci}
471bf215546Sopenharmony_ci
472bf215546Sopenharmony_ci/**
473bf215546Sopenharmony_ci * Allocate a buffer object for the given dimensions
474bf215546Sopenharmony_ci *
475bf215546Sopenharmony_ci * \param gbm The gbm device returned from gbm_create_device()
476bf215546Sopenharmony_ci * \param width The width for the buffer
477bf215546Sopenharmony_ci * \param height The height for the buffer
478bf215546Sopenharmony_ci * \param format The format to use for the buffer, from GBM_FORMAT_* or
479bf215546Sopenharmony_ci * GBM_BO_FORMAT_* tokens
480bf215546Sopenharmony_ci * \param flags The union of the usage flags for this buffer
481bf215546Sopenharmony_ci *
482bf215546Sopenharmony_ci * \return A newly allocated buffer that should be freed with gbm_bo_destroy()
483bf215546Sopenharmony_ci * when no longer needed. If an error occurs during allocation %NULL will be
484bf215546Sopenharmony_ci * returned and errno set.
485bf215546Sopenharmony_ci *
486bf215546Sopenharmony_ci * \sa enum gbm_bo_flags for the list of usage flags
487bf215546Sopenharmony_ci */
488bf215546Sopenharmony_ciGBM_EXPORT struct gbm_bo *
489bf215546Sopenharmony_cigbm_bo_create(struct gbm_device *gbm,
490bf215546Sopenharmony_ci              uint32_t width, uint32_t height,
491bf215546Sopenharmony_ci              uint32_t format, uint32_t flags)
492bf215546Sopenharmony_ci{
493bf215546Sopenharmony_ci   if (width == 0 || height == 0) {
494bf215546Sopenharmony_ci      errno = EINVAL;
495bf215546Sopenharmony_ci      return NULL;
496bf215546Sopenharmony_ci   }
497bf215546Sopenharmony_ci
498bf215546Sopenharmony_ci   return gbm->v0.bo_create(gbm, width, height, format, flags, NULL, 0);
499bf215546Sopenharmony_ci}
500bf215546Sopenharmony_ci
501bf215546Sopenharmony_ciGBM_EXPORT struct gbm_bo *
502bf215546Sopenharmony_cigbm_bo_create_with_modifiers(struct gbm_device *gbm,
503bf215546Sopenharmony_ci                             uint32_t width, uint32_t height,
504bf215546Sopenharmony_ci                             uint32_t format,
505bf215546Sopenharmony_ci                             const uint64_t *modifiers,
506bf215546Sopenharmony_ci                             const unsigned int count)
507bf215546Sopenharmony_ci{
508bf215546Sopenharmony_ci   uint32_t flags = 0;
509bf215546Sopenharmony_ci
510bf215546Sopenharmony_ci   /*
511bf215546Sopenharmony_ci    * ABI version 1 added the modifiers+flags capability. Backends from
512bf215546Sopenharmony_ci    * prior versions may fail if "unknown" flags are provided along with
513bf215546Sopenharmony_ci    * modifiers, but assume scanout is required when modifiers are used.
514bf215546Sopenharmony_ci    * Newer backends expect scanout to be explicitly requested if required,
515bf215546Sopenharmony_ci    * but applications using this older interface rely on the older implied
516bf215546Sopenharmony_ci    * requirement, so that behavior must be preserved.
517bf215546Sopenharmony_ci    */
518bf215546Sopenharmony_ci   if (gbm->v0.backend_version >= 1) {
519bf215546Sopenharmony_ci      flags |= GBM_BO_USE_SCANOUT;
520bf215546Sopenharmony_ci   }
521bf215546Sopenharmony_ci
522bf215546Sopenharmony_ci   return gbm_bo_create_with_modifiers2(gbm, width, height, format, modifiers,
523bf215546Sopenharmony_ci                                        count, flags);
524bf215546Sopenharmony_ci}
525bf215546Sopenharmony_ci
526bf215546Sopenharmony_ciGBM_EXPORT struct gbm_bo *
527bf215546Sopenharmony_cigbm_bo_create_with_modifiers2(struct gbm_device *gbm,
528bf215546Sopenharmony_ci                              uint32_t width, uint32_t height,
529bf215546Sopenharmony_ci                              uint32_t format,
530bf215546Sopenharmony_ci                              const uint64_t *modifiers,
531bf215546Sopenharmony_ci                              const unsigned int count,
532bf215546Sopenharmony_ci                              uint32_t flags)
533bf215546Sopenharmony_ci{
534bf215546Sopenharmony_ci   if (width == 0 || height == 0) {
535bf215546Sopenharmony_ci      errno = EINVAL;
536bf215546Sopenharmony_ci      return NULL;
537bf215546Sopenharmony_ci   }
538bf215546Sopenharmony_ci
539bf215546Sopenharmony_ci   if ((count && !modifiers) || (modifiers && !count)) {
540bf215546Sopenharmony_ci      errno = EINVAL;
541bf215546Sopenharmony_ci      return NULL;
542bf215546Sopenharmony_ci   }
543bf215546Sopenharmony_ci
544bf215546Sopenharmony_ci   if (modifiers && (flags & GBM_BO_USE_LINEAR)) {
545bf215546Sopenharmony_ci      errno = EINVAL;
546bf215546Sopenharmony_ci      return NULL;
547bf215546Sopenharmony_ci   }
548bf215546Sopenharmony_ci
549bf215546Sopenharmony_ci   return gbm->v0.bo_create(gbm, width, height, format, flags, modifiers, count);
550bf215546Sopenharmony_ci}
551bf215546Sopenharmony_ci
552bf215546Sopenharmony_ci/**
553bf215546Sopenharmony_ci * Create a gbm buffer object from a foreign object
554bf215546Sopenharmony_ci *
555bf215546Sopenharmony_ci * This function imports a foreign object and creates a new gbm bo for it.
556bf215546Sopenharmony_ci * This enables using the foreign object with a display API such as KMS.
557bf215546Sopenharmony_ci * Currently these types of foreign objects are supported, indicated by the type
558bf215546Sopenharmony_ci * argument:
559bf215546Sopenharmony_ci *
560bf215546Sopenharmony_ci *   GBM_BO_IMPORT_WL_BUFFER
561bf215546Sopenharmony_ci *   GBM_BO_IMPORT_EGL_IMAGE
562bf215546Sopenharmony_ci *   GBM_BO_IMPORT_FD
563bf215546Sopenharmony_ci *   GBM_BO_IMPORT_FD_MODIFIER
564bf215546Sopenharmony_ci *
565bf215546Sopenharmony_ci * The gbm bo shares the underlying pixels but its life-time is
566bf215546Sopenharmony_ci * independent of the foreign object.
567bf215546Sopenharmony_ci *
568bf215546Sopenharmony_ci * \param gbm The gbm device returned from gbm_create_device()
569bf215546Sopenharmony_ci * \param type The type of object we're importing
570bf215546Sopenharmony_ci * \param buffer Pointer to the external object
571bf215546Sopenharmony_ci * \param flags The union of the usage flags for this buffer
572bf215546Sopenharmony_ci *
573bf215546Sopenharmony_ci * \return A newly allocated buffer object that should be freed with
574bf215546Sopenharmony_ci * gbm_bo_destroy() when no longer needed. On error, %NULL is returned
575bf215546Sopenharmony_ci * and errno is set.
576bf215546Sopenharmony_ci *
577bf215546Sopenharmony_ci * \sa enum gbm_bo_flags for the list of usage flags
578bf215546Sopenharmony_ci */
579bf215546Sopenharmony_ciGBM_EXPORT struct gbm_bo *
580bf215546Sopenharmony_cigbm_bo_import(struct gbm_device *gbm,
581bf215546Sopenharmony_ci              uint32_t type, void *buffer, uint32_t flags)
582bf215546Sopenharmony_ci{
583bf215546Sopenharmony_ci   return gbm->v0.bo_import(gbm, type, buffer, flags);
584bf215546Sopenharmony_ci}
585bf215546Sopenharmony_ci
586bf215546Sopenharmony_ci/**
587bf215546Sopenharmony_ci * Map a region of a gbm buffer object for cpu access
588bf215546Sopenharmony_ci *
589bf215546Sopenharmony_ci * This function maps a region of a gbm bo for cpu read and/or write
590bf215546Sopenharmony_ci * access.
591bf215546Sopenharmony_ci *
592bf215546Sopenharmony_ci * The mapping exposes a linear view of the buffer object even if the buffer
593bf215546Sopenharmony_ci * has a non-linear modifier.
594bf215546Sopenharmony_ci *
595bf215546Sopenharmony_ci * This function may require intermediate buffer copies (ie. it may be slow).
596bf215546Sopenharmony_ci *
597bf215546Sopenharmony_ci * \param bo The buffer object
598bf215546Sopenharmony_ci * \param x The X (top left origin) starting position of the mapped region for
599bf215546Sopenharmony_ci * the buffer
600bf215546Sopenharmony_ci * \param y The Y (top left origin) starting position of the mapped region for
601bf215546Sopenharmony_ci * the buffer
602bf215546Sopenharmony_ci * \param width The width of the mapped region for the buffer
603bf215546Sopenharmony_ci * \param height The height of the mapped region for the buffer
604bf215546Sopenharmony_ci * \param flags The union of the GBM_BO_TRANSFER_* flags for this buffer
605bf215546Sopenharmony_ci * \param stride Ptr for returned stride in bytes of the mapped region
606bf215546Sopenharmony_ci * \param map_data Returned opaque ptr for the mapped region
607bf215546Sopenharmony_ci *
608bf215546Sopenharmony_ci * \return Address of the mapped buffer that should be unmapped with
609bf215546Sopenharmony_ci * gbm_bo_unmap() when no longer needed. On error, %NULL is returned
610bf215546Sopenharmony_ci * and errno is set.
611bf215546Sopenharmony_ci *
612bf215546Sopenharmony_ci * \sa enum gbm_bo_transfer_flags for the list of flags
613bf215546Sopenharmony_ci */
614bf215546Sopenharmony_ciGBM_EXPORT void *
615bf215546Sopenharmony_cigbm_bo_map(struct gbm_bo *bo,
616bf215546Sopenharmony_ci              uint32_t x, uint32_t y,
617bf215546Sopenharmony_ci              uint32_t width, uint32_t height,
618bf215546Sopenharmony_ci              uint32_t flags, uint32_t *stride, void **map_data)
619bf215546Sopenharmony_ci{
620bf215546Sopenharmony_ci   if (!bo || width == 0 || height == 0 || !stride || !map_data) {
621bf215546Sopenharmony_ci      errno = EINVAL;
622bf215546Sopenharmony_ci      return NULL;
623bf215546Sopenharmony_ci   }
624bf215546Sopenharmony_ci
625bf215546Sopenharmony_ci   return bo->gbm->v0.bo_map(bo, x, y, width, height,
626bf215546Sopenharmony_ci                             flags, stride, map_data);
627bf215546Sopenharmony_ci}
628bf215546Sopenharmony_ci
629bf215546Sopenharmony_ci/**
630bf215546Sopenharmony_ci * Unmap a previously mapped region of a gbm buffer object
631bf215546Sopenharmony_ci *
632bf215546Sopenharmony_ci * This function unmaps a region of a gbm bo for cpu read and/or write
633bf215546Sopenharmony_ci * access.
634bf215546Sopenharmony_ci *
635bf215546Sopenharmony_ci * \param bo The buffer object
636bf215546Sopenharmony_ci * \param map_data opaque ptr returned from prior gbm_bo_map
637bf215546Sopenharmony_ci */
638bf215546Sopenharmony_ciGBM_EXPORT void
639bf215546Sopenharmony_cigbm_bo_unmap(struct gbm_bo *bo, void *map_data)
640bf215546Sopenharmony_ci{
641bf215546Sopenharmony_ci   bo->gbm->v0.bo_unmap(bo, map_data);
642bf215546Sopenharmony_ci}
643bf215546Sopenharmony_ci
644bf215546Sopenharmony_ci/**
645bf215546Sopenharmony_ci * Allocate a surface object
646bf215546Sopenharmony_ci *
647bf215546Sopenharmony_ci * \param gbm The gbm device returned from gbm_create_device()
648bf215546Sopenharmony_ci * \param width The width for the surface
649bf215546Sopenharmony_ci * \param height The height for the surface
650bf215546Sopenharmony_ci * \param format The format to use for the surface
651bf215546Sopenharmony_ci *
652bf215546Sopenharmony_ci * \return A newly allocated surface that should be freed with
653bf215546Sopenharmony_ci * gbm_surface_destroy() when no longer needed. If an error occurs
654bf215546Sopenharmony_ci * during allocation %NULL will be returned.
655bf215546Sopenharmony_ci *
656bf215546Sopenharmony_ci * \sa enum gbm_bo_format for the list of formats
657bf215546Sopenharmony_ci */
658bf215546Sopenharmony_ciGBM_EXPORT struct gbm_surface *
659bf215546Sopenharmony_cigbm_surface_create(struct gbm_device *gbm,
660bf215546Sopenharmony_ci                   uint32_t width, uint32_t height,
661bf215546Sopenharmony_ci		   uint32_t format, uint32_t flags)
662bf215546Sopenharmony_ci{
663bf215546Sopenharmony_ci   return gbm->v0.surface_create(gbm, width, height, format, flags, NULL, 0);
664bf215546Sopenharmony_ci}
665bf215546Sopenharmony_ci
666bf215546Sopenharmony_ciGBM_EXPORT struct gbm_surface *
667bf215546Sopenharmony_cigbm_surface_create_with_modifiers(struct gbm_device *gbm,
668bf215546Sopenharmony_ci                                  uint32_t width, uint32_t height,
669bf215546Sopenharmony_ci                                  uint32_t format,
670bf215546Sopenharmony_ci                                  const uint64_t *modifiers,
671bf215546Sopenharmony_ci                                  const unsigned int count)
672bf215546Sopenharmony_ci{
673bf215546Sopenharmony_ci   uint32_t flags = 0;
674bf215546Sopenharmony_ci
675bf215546Sopenharmony_ci   /*
676bf215546Sopenharmony_ci    * ABI version 1 added the modifiers+flags capability. Backends from
677bf215546Sopenharmony_ci    * prior versions may fail if "unknown" flags are provided along with
678bf215546Sopenharmony_ci    * modifiers, but assume scanout is required when modifiers are used.
679bf215546Sopenharmony_ci    * Newer backends expect scanout to be explicitly requested if required,
680bf215546Sopenharmony_ci    * but applications using this older interface rely on the older implied
681bf215546Sopenharmony_ci    * requirement, so that behavior must be preserved.
682bf215546Sopenharmony_ci    */
683bf215546Sopenharmony_ci   if (gbm->v0.backend_version >= 1) {
684bf215546Sopenharmony_ci      flags |= GBM_BO_USE_SCANOUT;
685bf215546Sopenharmony_ci   }
686bf215546Sopenharmony_ci
687bf215546Sopenharmony_ci   return gbm_surface_create_with_modifiers2(gbm, width, height, format,
688bf215546Sopenharmony_ci                                             modifiers, count,
689bf215546Sopenharmony_ci                                             flags);
690bf215546Sopenharmony_ci}
691bf215546Sopenharmony_ci
692bf215546Sopenharmony_ciGBM_EXPORT struct gbm_surface *
693bf215546Sopenharmony_cigbm_surface_create_with_modifiers2(struct gbm_device *gbm,
694bf215546Sopenharmony_ci                                   uint32_t width, uint32_t height,
695bf215546Sopenharmony_ci                                   uint32_t format,
696bf215546Sopenharmony_ci                                   const uint64_t *modifiers,
697bf215546Sopenharmony_ci                                   const unsigned int count,
698bf215546Sopenharmony_ci                                   uint32_t flags)
699bf215546Sopenharmony_ci{
700bf215546Sopenharmony_ci   if ((count && !modifiers) || (modifiers && !count)) {
701bf215546Sopenharmony_ci      errno = EINVAL;
702bf215546Sopenharmony_ci      return NULL;
703bf215546Sopenharmony_ci   }
704bf215546Sopenharmony_ci
705bf215546Sopenharmony_ci   if (modifiers && (flags & GBM_BO_USE_LINEAR)) {
706bf215546Sopenharmony_ci      errno = EINVAL;
707bf215546Sopenharmony_ci      return NULL;
708bf215546Sopenharmony_ci   }
709bf215546Sopenharmony_ci
710bf215546Sopenharmony_ci   return gbm->v0.surface_create(gbm, width, height, format, flags,
711bf215546Sopenharmony_ci                                 modifiers, count);
712bf215546Sopenharmony_ci}
713bf215546Sopenharmony_ci
714bf215546Sopenharmony_ci/**
715bf215546Sopenharmony_ci * Destroys the given surface and frees all resources associated with it.
716bf215546Sopenharmony_ci *
717bf215546Sopenharmony_ci * Prior to calling this function all buffers locked with
718bf215546Sopenharmony_ci * gbm_surface_lock_front_buffer() need to be released and the associated
719bf215546Sopenharmony_ci * EGL surface destroyed.
720bf215546Sopenharmony_ci *
721bf215546Sopenharmony_ci * \param surf The surface
722bf215546Sopenharmony_ci */
723bf215546Sopenharmony_ciGBM_EXPORT void
724bf215546Sopenharmony_cigbm_surface_destroy(struct gbm_surface *surf)
725bf215546Sopenharmony_ci{
726bf215546Sopenharmony_ci   surf->gbm->v0.surface_destroy(surf);
727bf215546Sopenharmony_ci}
728bf215546Sopenharmony_ci
729bf215546Sopenharmony_ci/**
730bf215546Sopenharmony_ci * Lock the surface's current front buffer
731bf215546Sopenharmony_ci *
732bf215546Sopenharmony_ci * Lock rendering to the surface's current front buffer until it is
733bf215546Sopenharmony_ci * released with gbm_surface_release_buffer().
734bf215546Sopenharmony_ci *
735bf215546Sopenharmony_ci * This function must be called exactly once after calling
736bf215546Sopenharmony_ci * eglSwapBuffers.  Calling it before any eglSwapBuffer has happened
737bf215546Sopenharmony_ci * on the surface or two or more times after eglSwapBuffers is an error.
738bf215546Sopenharmony_ci *
739bf215546Sopenharmony_ci * \param surf The surface
740bf215546Sopenharmony_ci *
741bf215546Sopenharmony_ci * \return A buffer object representing the front buffer that should be
742bf215546Sopenharmony_ci * released with gbm_surface_release_buffer() when no longer needed and before
743bf215546Sopenharmony_ci * the associated EGL surface gets destroyed. The implementation is free to
744bf215546Sopenharmony_ci * reuse buffers released with gbm_surface_release_buffer() so this bo should
745bf215546Sopenharmony_ci * not be destroyed using gbm_bo_destroy(). If an error occurs this function
746bf215546Sopenharmony_ci * returns %NULL.
747bf215546Sopenharmony_ci */
748bf215546Sopenharmony_ciGBM_EXPORT struct gbm_bo *
749bf215546Sopenharmony_cigbm_surface_lock_front_buffer(struct gbm_surface *surf)
750bf215546Sopenharmony_ci{
751bf215546Sopenharmony_ci   return surf->gbm->v0.surface_lock_front_buffer(surf);
752bf215546Sopenharmony_ci}
753bf215546Sopenharmony_ci
754bf215546Sopenharmony_ci/**
755bf215546Sopenharmony_ci * Release a locked buffer obtained with gbm_surface_lock_front_buffer()
756bf215546Sopenharmony_ci *
757bf215546Sopenharmony_ci * Returns the underlying buffer to the gbm surface.  Releasing a bo
758bf215546Sopenharmony_ci * will typically make gbm_surface_has_free_buffer() return 1 and thus
759bf215546Sopenharmony_ci * allow rendering the next frame, but not always. The implementation
760bf215546Sopenharmony_ci * may choose to destroy the bo immediately or reuse it, in which case
761bf215546Sopenharmony_ci * the user data associated with it is unchanged.
762bf215546Sopenharmony_ci *
763bf215546Sopenharmony_ci * \param surf The surface
764bf215546Sopenharmony_ci * \param bo The buffer object
765bf215546Sopenharmony_ci */
766bf215546Sopenharmony_ciGBM_EXPORT void
767bf215546Sopenharmony_cigbm_surface_release_buffer(struct gbm_surface *surf, struct gbm_bo *bo)
768bf215546Sopenharmony_ci{
769bf215546Sopenharmony_ci   surf->gbm->v0.surface_release_buffer(surf, bo);
770bf215546Sopenharmony_ci}
771bf215546Sopenharmony_ci
772bf215546Sopenharmony_ci/**
773bf215546Sopenharmony_ci * Return whether or not a surface has free (non-locked) buffers
774bf215546Sopenharmony_ci *
775bf215546Sopenharmony_ci * Before starting a new frame, the surface must have a buffer
776bf215546Sopenharmony_ci * available for rendering.  Initially, a gbm surface will have a free
777bf215546Sopenharmony_ci * buffer, but after one or more buffers have been locked (\sa
778bf215546Sopenharmony_ci * gbm_surface_lock_front_buffer()), the application must check for a
779bf215546Sopenharmony_ci * free buffer before rendering.
780bf215546Sopenharmony_ci *
781bf215546Sopenharmony_ci * If a surface doesn't have a free buffer, the application must
782bf215546Sopenharmony_ci * return a buffer to the surface using gbm_surface_release_buffer()
783bf215546Sopenharmony_ci * and after that, the application can query for free buffers again.
784bf215546Sopenharmony_ci *
785bf215546Sopenharmony_ci * \param surf The surface
786bf215546Sopenharmony_ci * \return 1 if the surface has free buffers, 0 otherwise
787bf215546Sopenharmony_ci */
788bf215546Sopenharmony_ciGBM_EXPORT int
789bf215546Sopenharmony_cigbm_surface_has_free_buffers(struct gbm_surface *surf)
790bf215546Sopenharmony_ci{
791bf215546Sopenharmony_ci   return surf->gbm->v0.surface_has_free_buffers(surf);
792bf215546Sopenharmony_ci}
793bf215546Sopenharmony_ci
794bf215546Sopenharmony_ci/* The two GBM_BO_FORMAT_[XA]RGB8888 formats alias the GBM_FORMAT_*
795bf215546Sopenharmony_ci * formats of the same name. We want to accept them whenever someone
796bf215546Sopenharmony_ci * has a GBM format, but never return them to the user. */
797bf215546Sopenharmony_cistatic uint32_t
798bf215546Sopenharmony_ciformat_canonicalize(uint32_t gbm_format)
799bf215546Sopenharmony_ci{
800bf215546Sopenharmony_ci   switch (gbm_format) {
801bf215546Sopenharmony_ci   case GBM_BO_FORMAT_XRGB8888:
802bf215546Sopenharmony_ci      return GBM_FORMAT_XRGB8888;
803bf215546Sopenharmony_ci   case GBM_BO_FORMAT_ARGB8888:
804bf215546Sopenharmony_ci      return GBM_FORMAT_ARGB8888;
805bf215546Sopenharmony_ci   default:
806bf215546Sopenharmony_ci      return gbm_format;
807bf215546Sopenharmony_ci   }
808bf215546Sopenharmony_ci}
809bf215546Sopenharmony_ci
810bf215546Sopenharmony_ci/**
811bf215546Sopenharmony_ci * Returns a string representing the fourcc format name.
812bf215546Sopenharmony_ci *
813bf215546Sopenharmony_ci * \param desc Caller-provided storage for the format name string.
814bf215546Sopenharmony_ci * \return String containing the fourcc of the format.
815bf215546Sopenharmony_ci */
816bf215546Sopenharmony_ciGBM_EXPORT char *
817bf215546Sopenharmony_cigbm_format_get_name(uint32_t gbm_format, struct gbm_format_name_desc *desc)
818bf215546Sopenharmony_ci{
819bf215546Sopenharmony_ci   gbm_format = format_canonicalize(gbm_format);
820bf215546Sopenharmony_ci
821bf215546Sopenharmony_ci   desc->name[0] = gbm_format;
822bf215546Sopenharmony_ci   desc->name[1] = gbm_format >> 8;
823bf215546Sopenharmony_ci   desc->name[2] = gbm_format >> 16;
824bf215546Sopenharmony_ci   desc->name[3] = gbm_format >> 24;
825bf215546Sopenharmony_ci   desc->name[4] = 0;
826bf215546Sopenharmony_ci
827bf215546Sopenharmony_ci   return desc->name;
828bf215546Sopenharmony_ci}
829bf215546Sopenharmony_ci
830bf215546Sopenharmony_ci/**
831bf215546Sopenharmony_ci * A global table of functions and global variables defined in the core GBM
832bf215546Sopenharmony_ci * code that need to be accessed directly by GBM backends.
833bf215546Sopenharmony_ci */
834bf215546Sopenharmony_cistruct gbm_core gbm_core = {
835bf215546Sopenharmony_ci   .v0.core_version = GBM_BACKEND_ABI_VERSION,
836bf215546Sopenharmony_ci   .v0.format_canonicalize = format_canonicalize,
837bf215546Sopenharmony_ci};
838