Monado OpenXR Runtime
comp_gl_client.h
Go to the documentation of this file.
1 // Copyright 2019-2022, Collabora, Ltd.
2 // SPDX-License-Identifier: BSL-1.0
3 /*!
4  * @file
5  * @brief OpenGL client side glue to compositor header.
6  * @author Jakob Bornecrantz <jakob@collabora.com>
7  * @ingroup comp_client
8  */
9 
10 #pragma once
11 
12 #include "xrt/xrt_compositor.h"
13 #include "os/os_threading.h"
14 
15 #ifdef __cplusplus
16 extern "C" {
17 #endif
18 
19 /*
20  *
21  * Structs
22  *
23  */
24 
26 
27 /*!
28  * @class client_gl_swapchain
29  *
30  * Wraps the real compositor swapchain providing a OpenGL based interface.
31  *
32  * Almost a one to one mapping to a OpenXR swapchain.
33  *
34  * @ingroup comp_client
35  * @implements xrt_swapchain_gl
36  */
38 {
39  //! Implements @ref xrt_swapchain_gl
40  struct xrt_swapchain_gl base;
41 
42  struct xrt_swapchain_native *xscn;
43 
44  //! The texture target of images in this swapchain.
45  uint32_t tex_target;
46 
47  /*!
48  * The compositor this swapchain was created on. Used when swapchain functions need to use the GL context.
49  *
50  * Not an owning pointer.
51  */
53 };
54 
55 /*!
56  * What's the reason to make the context current, this is needed currently for
57  * EGL where we have to create a shared context in some cases. But when we
58  * want to synchronize (insert a fence or call glFinish) we can not use the
59  * shared context and must use the context that the app provided on creation.
60  */
62 {
63  /*!
64  * Used when the compositor needs to insert a fence in the command
65  * stream of the apps context, this needs to be done in the given
66  * context and not the shared one that may be created.
67  */
69  /*!
70  * Any other reason to make the context current,
71  * the shared may be used by now.
72  */
74 };
75 
76 /*!
77  * Fetches the OpenGL context that is current on this thread and makes the
78  * OpenGL context given in the graphics binding current instead. Only one thread
79  * at a time can operate on the sections between
80  * @ref client_gl_context_begin_locked_func_t and
81  * @ref client_gl_context_end_locked_func_t,
82  * therefore @ref client_gl_context_end_locked_func_t MUST be called to avoid
83  * blocking the next thread calling @ref client_gl_context_begin_locked_func_t.
84  *
85  * This function must be called with the context_mutex locked held, that is
86  * handled by the helper function @ref client_gl_compositor_context_begin.
87  *
88  * If the return value is not XRT_SUCCESS,
89  * @ref client_gl_context_end_locked_func_t should not be called.
90  */
92  enum client_gl_context_reason reason);
93 
94 /*!
95  * Makes the OpenGL context current that was current before
96  * @ref client_gl_context_begin_locked_func_t was called.
97  *
98  * This function must be called with the context_mutex locked held, successful
99  * call to @ref client_gl_compositor_context_begin will ensure that. The lock is
100  * not released by this function, but @ref client_gl_compositor_context_end does
101  * release it.
102  */
104 
105 /*!
106  * The type of a swapchain create constructor.
107  *
108  * Because our swapchain creation varies depending on available extensions and
109  * application choices, the swapchain constructor parameter to
110  * client_gl_compositor is parameterized.
111  *
112  * Note that the "common" swapchain creation function does some setup before
113  * invoking this, and some cleanup after.
114  *
115  * - Must populate `destroy`
116  * - Does not need to save/restore texture binding
117  */
118 typedef struct xrt_swapchain *(*client_gl_swapchain_create_func_t)(struct xrt_compositor *xc,
119  const struct xrt_swapchain_create_info *info,
120  struct xrt_swapchain_native *xscn,
121  struct client_gl_swapchain **out_sc);
122 
123 /*!
124  * The type of a fence insertion function.
125  *
126  * This function is called in xrt_compositor::layer_commit.
127  *
128  * The returned graphics sync handle is given to xrt_compositor::layer_commit.
129  */
131  xrt_graphics_sync_handle_t *out_handle);
132 
133 /*!
134  * @class client_gl_compositor
135  *
136  * Wraps the real compositor providing a OpenGL based interface.
137  *
138  * @ingroup comp_client
139  * @implements xrt_compositor_gl
140  */
142 {
143  struct xrt_compositor_gl base;
144 
145  struct xrt_compositor_native *xcn;
146 
147  /*!
148  * Function pointer for making the OpenGL context current.
149  */
151 
152  /*!
153  * Function pointer for restoring prior OpenGL context.
154  */
156 
157  /*!
158  * Function pointer for creating the client swapchain.
159  */
161 
162  /*!
163  * Function pointer for inserting fences on
164  * xrt_compositor::layer_commit.
165  */
167 
168  /*!
169  * @ref client_gl_xlib_compositor::app_context can only be current on one thread; block other threads while we
170  * know it is bound to a thread.
171  */
172  struct os_mutex context_mutex;
173 
174  bool renderdoc_enabled;
175 };
176 
177 
178 /*
179  *
180  * Functions and helpers.
181  *
182  */
183 
184 /*!
185  * Down-cast helper.
186  * @protected @memberof client_gl_compositor
187  */
188 static inline struct client_gl_compositor *
190 {
191  return (struct client_gl_compositor *)xc;
192 }
193 
194 /*!
195  * Fill in a client_gl_compositor and do common OpenGL readiness checking.
196  *
197  * OpenGL can have multiple backing window systems we have to interact with, so
198  * there isn't just one unified OpenGL client constructor.
199  *
200  * Moves ownership of provided xcn to the client_gl_compositor.
201  *
202  * Be sure to load your GL loader/wrapper (GLAD) before calling into here, it
203  * won't be called for you.
204  *
205  * @public @memberof client_gl_compositor
206  * @see xrt_compositor_native
207  */
208 bool
210  struct xrt_compositor_native *xcn,
215 
216 /*!
217  * Free all resources from the client_gl_compositor, does not free the
218  * @ref client_gl_compositor itself. Nor does it free the
219  * @ref xrt_compositor_native given at init as that is not owned by us.
220  *
221  * @public @memberof client_gl_compositor
222  */
223 void
225 
226 /*!
227  * @copydoc client_gl_context_begin_locked_func_t
228  *
229  * Helper for calling through the function pointer.
230  *
231  * @public @memberof client_gl_compositor
232  */
233 static inline xrt_result_t
235 {
236  struct client_gl_compositor *cgc = client_gl_compositor(xc);
237 
239 
240  xrt_result_t xret = cgc->context_begin_locked(xc, reason);
241  if (xret != XRT_SUCCESS) {
243  }
244 
245  return xret;
246 }
247 
248 /*!
249  * @copydoc client_gl_context_end_locked_func_t
250  *
251  * Helper for calling through the function pointer.
252  *
253  * @public @memberof client_gl_compositor
254  */
255 static inline void
257 {
258  struct client_gl_compositor *cgc = client_gl_compositor(xc);
259 
260  cgc->context_end_locked(xc, reason);
261 
263 }
264 
265 
266 #ifdef __cplusplus
267 }
268 #endif
xrt_result_t(* client_gl_insert_fence_func_t)(struct xrt_compositor *xc, xrt_graphics_sync_handle_t *out_handle)
The type of a fence insertion function.
Definition: comp_gl_client.h:130
struct xrt_swapchain *(* client_gl_swapchain_create_func_t)(struct xrt_compositor *xc, const struct xrt_swapchain_create_info *info, struct xrt_swapchain_native *xscn, struct client_gl_swapchain **out_sc)
The type of a swapchain create constructor.
Definition: comp_gl_client.h:118
xrt_result_t(* client_gl_context_begin_locked_func_t)(struct xrt_compositor *xc, enum client_gl_context_reason reason)
Fetches the OpenGL context that is current on this thread and makes the OpenGL context given in the g...
Definition: comp_gl_client.h:91
client_gl_context_reason
What's the reason to make the context current, this is needed currently for EGL where we have to crea...
Definition: comp_gl_client.h:62
@ CLIENT_GL_CONTEXT_REASON_SYNCHRONIZE
Used when the compositor needs to insert a fence in the command stream of the apps context,...
Definition: comp_gl_client.h:68
@ CLIENT_GL_CONTEXT_REASON_OTHER
Any other reason to make the context current, the shared may be used by now.
Definition: comp_gl_client.h:73
void(* client_gl_context_end_locked_func_t)(struct xrt_compositor *xc, enum client_gl_context_reason reason)
Makes the OpenGL context current that was current before client_gl_context_begin_locked_func_t was ca...
Definition: comp_gl_client.h:103
static void os_mutex_lock(struct os_mutex *om)
Lock.
Definition: os_threading.h:86
static void os_mutex_unlock(struct os_mutex *om)
Unlock.
Definition: os_threading.h:110
enum xrt_result xrt_result_t
Result type used across Monado.
@ XRT_SUCCESS
The operation succeeded.
Definition: xrt_results.h:26
Wrapper around OS threading native functions.
Wraps the real compositor providing a OpenGL based interface.
Definition: comp_gl_client.h:142
struct os_mutex context_mutex
client_gl_xlib_compositor::app_context can only be current on one thread; block other threads while w...
Definition: comp_gl_client.h:172
static void client_gl_compositor_context_end(struct xrt_compositor *xc, enum client_gl_context_reason reason)
Makes the OpenGL context current that was current before client_gl_context_begin_locked_func_t was ca...
Definition: comp_gl_client.h:256
static xrt_result_t client_gl_compositor_context_begin(struct xrt_compositor *xc, enum client_gl_context_reason reason)
Fetches the OpenGL context that is current on this thread and makes the OpenGL context given in the g...
Definition: comp_gl_client.h:234
client_gl_swapchain_create_func_t create_swapchain
Function pointer for creating the client swapchain.
Definition: comp_gl_client.h:160
bool client_gl_compositor_init(struct client_gl_compositor *c, struct xrt_compositor_native *xcn, client_gl_context_begin_locked_func_t context_begin, client_gl_context_end_locked_func_t context_end, client_gl_swapchain_create_func_t create_swapchain, client_gl_insert_fence_func_t insert_fence)
Fill in a client_gl_compositor and do common OpenGL readiness checking.
Definition: comp_gl_client.c:588
static struct client_gl_compositor * client_gl_compositor(struct xrt_compositor *xc)
Down-cast helper.
Definition: comp_gl_client.h:189
client_gl_insert_fence_func_t insert_fence
Function pointer for inserting fences on xrt_compositor::layer_commit.
Definition: comp_gl_client.h:166
void client_gl_compositor_close(struct client_gl_compositor *c)
Free all resources from the client_gl_compositor, does not free the client_gl_compositor itself.
Definition: comp_gl_client.c:582
client_gl_context_end_locked_func_t context_end_locked
Function pointer for restoring prior OpenGL context.
Definition: comp_gl_client.h:155
client_gl_context_begin_locked_func_t context_begin_locked
Function pointer for making the OpenGL context current.
Definition: comp_gl_client.h:150
Wraps the real compositor swapchain providing a OpenGL based interface.
Definition: comp_gl_client.h:38
uint32_t tex_target
The texture target of images in this swapchain.
Definition: comp_gl_client.h:45
struct client_gl_compositor * gl_compositor
The compositor this swapchain was created on.
Definition: comp_gl_client.h:52
struct xrt_swapchain_gl base
Implements xrt_swapchain_gl.
Definition: comp_gl_client.h:40
A wrapper around a native mutex.
Definition: os_threading.h:55
Base class for an OpenGL (ES) client compositor.
Definition: xrt_compositor.h:1938
Main compositor server interface.
Definition: xrt_compositor.h:2196
Common compositor client interface/base.
Definition: xrt_compositor.h:986
Swapchain creation info.
Definition: xrt_compositor.h:876
Base class for an OpenGL (ES) client swapchain.
Definition: xrt_compositor.h:1923
Base class for a swapchain that exposes a native buffer handle to be imported into a client API.
Definition: xrt_compositor.h:2163
Common swapchain interface/base.
Definition: xrt_compositor.h:536
Header declaring XRT graphics interfaces.
int xrt_graphics_sync_handle_t
The type underlying synchronization primitives (semaphores, etc) shared between compositor clients an...
Definition: xrt_handles.h:348