1b8e80941Smrg/* 2b8e80941Smrg * Copyright © 2016 Red Hat. 3b8e80941Smrg * 4b8e80941Smrg * Permission is hereby granted, free of charge, to any person obtaining a 5b8e80941Smrg * copy of this software and associated documentation files (the "Software"), 6b8e80941Smrg * to deal in the Software without restriction, including without limitation 7b8e80941Smrg * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8b8e80941Smrg * and/or sell copies of the Software, and to permit persons to whom the 9b8e80941Smrg * Software is furnished to do so, subject to the following conditions: 10b8e80941Smrg * 11b8e80941Smrg * The above copyright notice and this permission notice (including the next 12b8e80941Smrg * paragraph) shall be included in all copies or substantial portions of the 13b8e80941Smrg * Software. 14b8e80941Smrg * 15b8e80941Smrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16b8e80941Smrg * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17b8e80941Smrg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 18b8e80941Smrg * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19b8e80941Smrg * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20b8e80941Smrg * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 21b8e80941Smrg * DEALINGS IN THE SOFTWARE. 22b8e80941Smrg */ 23b8e80941Smrg 24b8e80941Smrg#include "macros.h" 25b8e80941Smrg#include "mtypes.h" 26b8e80941Smrg#include "bufferobj.h" 27b8e80941Smrg#include "context.h" 28b8e80941Smrg#include "externalobjects.h" 29b8e80941Smrg#include "teximage.h" 30b8e80941Smrg#include "texobj.h" 31b8e80941Smrg#include "glformats.h" 32b8e80941Smrg#include "texstorage.h" 33b8e80941Smrg 34b8e80941Smrg/** 35b8e80941Smrg * Allocate and initialize a new memory object. But don't put it into the 36b8e80941Smrg * memory object hash table. 37b8e80941Smrg * 38b8e80941Smrg * Called via ctx->Driver.NewMemoryObject, unless overridden by a device 39b8e80941Smrg * driver. 40b8e80941Smrg * 41b8e80941Smrg * \return pointer to new memory object. 42b8e80941Smrg */ 43b8e80941Smrgstatic struct gl_memory_object * 44b8e80941Smrg_mesa_new_memory_object(struct gl_context *ctx, GLuint name) 45b8e80941Smrg{ 46b8e80941Smrg struct gl_memory_object *obj = MALLOC_STRUCT(gl_memory_object); 47b8e80941Smrg if (!obj) 48b8e80941Smrg return NULL; 49b8e80941Smrg 50b8e80941Smrg _mesa_initialize_memory_object(ctx, obj, name); 51b8e80941Smrg return obj; 52b8e80941Smrg} 53b8e80941Smrg 54b8e80941Smrg/** 55b8e80941Smrg * Delete a memory object. Called via ctx->Driver.DeleteMemory(). 56b8e80941Smrg * Not removed from hash table here. 57b8e80941Smrg */ 58b8e80941Smrgvoid 59b8e80941Smrg_mesa_delete_memory_object(struct gl_context *ctx, 60b8e80941Smrg struct gl_memory_object *memObj) 61b8e80941Smrg{ 62b8e80941Smrg free(memObj); 63b8e80941Smrg} 64b8e80941Smrg 65b8e80941Smrgvoid 66b8e80941Smrg_mesa_init_memory_object_functions(struct dd_function_table *driver) 67b8e80941Smrg{ 68b8e80941Smrg driver->NewMemoryObject = _mesa_new_memory_object; 69b8e80941Smrg driver->DeleteMemoryObject = _mesa_delete_memory_object; 70b8e80941Smrg} 71b8e80941Smrg 72b8e80941Smrg/** 73b8e80941Smrg * Initialize a buffer object to default values. 74b8e80941Smrg */ 75b8e80941Smrgvoid 76b8e80941Smrg_mesa_initialize_memory_object(struct gl_context *ctx, 77b8e80941Smrg struct gl_memory_object *obj, 78b8e80941Smrg GLuint name) 79b8e80941Smrg{ 80b8e80941Smrg memset(obj, 0, sizeof(struct gl_memory_object)); 81b8e80941Smrg obj->Name = name; 82b8e80941Smrg obj->Dedicated = GL_FALSE; 83b8e80941Smrg} 84b8e80941Smrg 85b8e80941Smrgvoid GLAPIENTRY 86b8e80941Smrg_mesa_DeleteMemoryObjectsEXT(GLsizei n, const GLuint *memoryObjects) 87b8e80941Smrg{ 88b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 89b8e80941Smrg 90b8e80941Smrg if (MESA_VERBOSE & (VERBOSE_API)) { 91b8e80941Smrg _mesa_debug(ctx, "glDeleteMemoryObjectsEXT(%d, %p)\n", n, 92b8e80941Smrg memoryObjects); 93b8e80941Smrg } 94b8e80941Smrg 95b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 96b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, 97b8e80941Smrg "glDeleteMemoryObjectsEXT(unsupported)"); 98b8e80941Smrg return; 99b8e80941Smrg } 100b8e80941Smrg 101b8e80941Smrg if (n < 0) { 102b8e80941Smrg _mesa_error(ctx, GL_INVALID_VALUE, "glDeleteMemoryObjectsEXT(n < 0)"); 103b8e80941Smrg return; 104b8e80941Smrg } 105b8e80941Smrg 106b8e80941Smrg if (!memoryObjects) 107b8e80941Smrg return; 108b8e80941Smrg 109b8e80941Smrg _mesa_HashLockMutex(ctx->Shared->MemoryObjects); 110b8e80941Smrg for (GLint i = 0; i < n; i++) { 111b8e80941Smrg if (memoryObjects[i] > 0) { 112b8e80941Smrg struct gl_memory_object *delObj 113b8e80941Smrg = _mesa_lookup_memory_object_locked(ctx, memoryObjects[i]); 114b8e80941Smrg 115b8e80941Smrg if (delObj) { 116b8e80941Smrg _mesa_HashRemoveLocked(ctx->Shared->MemoryObjects, 117b8e80941Smrg memoryObjects[i]); 118b8e80941Smrg ctx->Driver.DeleteMemoryObject(ctx, delObj); 119b8e80941Smrg } 120b8e80941Smrg } 121b8e80941Smrg } 122b8e80941Smrg _mesa_HashUnlockMutex(ctx->Shared->MemoryObjects); 123b8e80941Smrg} 124b8e80941Smrg 125b8e80941SmrgGLboolean GLAPIENTRY 126b8e80941Smrg_mesa_IsMemoryObjectEXT(GLuint memoryObject) 127b8e80941Smrg{ 128b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 129b8e80941Smrg 130b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 131b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, 132b8e80941Smrg "glIsMemoryObjectEXT(unsupported)"); 133b8e80941Smrg return GL_FALSE; 134b8e80941Smrg } 135b8e80941Smrg 136b8e80941Smrg struct gl_memory_object *obj = 137b8e80941Smrg _mesa_lookup_memory_object(ctx, memoryObject); 138b8e80941Smrg 139b8e80941Smrg return obj ? GL_TRUE : GL_FALSE; 140b8e80941Smrg} 141b8e80941Smrg 142b8e80941Smrgvoid GLAPIENTRY 143b8e80941Smrg_mesa_CreateMemoryObjectsEXT(GLsizei n, GLuint *memoryObjects) 144b8e80941Smrg{ 145b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 146b8e80941Smrg 147b8e80941Smrg const char *func = "glCreateMemoryObjectsEXT"; 148b8e80941Smrg 149b8e80941Smrg if (MESA_VERBOSE & (VERBOSE_API)) 150b8e80941Smrg _mesa_debug(ctx, "%s(%d, %p)", func, n, memoryObjects); 151b8e80941Smrg 152b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 153b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 154b8e80941Smrg return; 155b8e80941Smrg } 156b8e80941Smrg 157b8e80941Smrg if (n < 0) { 158b8e80941Smrg _mesa_error(ctx, GL_INVALID_VALUE, "%s(n < 0)", func); 159b8e80941Smrg return; 160b8e80941Smrg } 161b8e80941Smrg 162b8e80941Smrg if (!memoryObjects) 163b8e80941Smrg return; 164b8e80941Smrg 165b8e80941Smrg _mesa_HashLockMutex(ctx->Shared->MemoryObjects); 166b8e80941Smrg GLuint first = _mesa_HashFindFreeKeyBlock(ctx->Shared->MemoryObjects, n); 167b8e80941Smrg if (first) { 168b8e80941Smrg for (GLsizei i = 0; i < n; i++) { 169b8e80941Smrg struct gl_memory_object *memObj; 170b8e80941Smrg 171b8e80941Smrg memoryObjects[i] = first + i; 172b8e80941Smrg 173b8e80941Smrg /* allocate memory object */ 174b8e80941Smrg memObj = ctx->Driver.NewMemoryObject(ctx, memoryObjects[i]); 175b8e80941Smrg if (!memObj) { 176b8e80941Smrg _mesa_error(ctx, GL_OUT_OF_MEMORY, "%s()", func); 177b8e80941Smrg _mesa_HashUnlockMutex(ctx->Shared->MemoryObjects); 178b8e80941Smrg return; 179b8e80941Smrg } 180b8e80941Smrg 181b8e80941Smrg /* insert into hash table */ 182b8e80941Smrg _mesa_HashInsertLocked(ctx->Shared->MemoryObjects, 183b8e80941Smrg memoryObjects[i], 184b8e80941Smrg memObj); 185b8e80941Smrg } 186b8e80941Smrg } 187b8e80941Smrg 188b8e80941Smrg _mesa_HashUnlockMutex(ctx->Shared->MemoryObjects); 189b8e80941Smrg} 190b8e80941Smrg 191b8e80941Smrgvoid GLAPIENTRY 192b8e80941Smrg_mesa_MemoryObjectParameterivEXT(GLuint memoryObject, 193b8e80941Smrg GLenum pname, 194b8e80941Smrg const GLint *params) 195b8e80941Smrg{ 196b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 197b8e80941Smrg struct gl_memory_object *memObj; 198b8e80941Smrg 199b8e80941Smrg const char *func = "glMemoryObjectParameterivEXT"; 200b8e80941Smrg 201b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 202b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 203b8e80941Smrg return; 204b8e80941Smrg } 205b8e80941Smrg 206b8e80941Smrg memObj = _mesa_lookup_memory_object(ctx, memoryObject); 207b8e80941Smrg if (!memObj) 208b8e80941Smrg return; 209b8e80941Smrg 210b8e80941Smrg if (memObj->Immutable) { 211b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(memoryObject is immutable", func); 212b8e80941Smrg return; 213b8e80941Smrg } 214b8e80941Smrg 215b8e80941Smrg switch (pname) { 216b8e80941Smrg case GL_DEDICATED_MEMORY_OBJECT_EXT: 217b8e80941Smrg memObj->Dedicated = (GLboolean) params[0]; 218b8e80941Smrg break; 219b8e80941Smrg case GL_PROTECTED_MEMORY_OBJECT_EXT: 220b8e80941Smrg /* EXT_protected_textures not supported */ 221b8e80941Smrg goto invalid_pname; 222b8e80941Smrg default: 223b8e80941Smrg goto invalid_pname; 224b8e80941Smrg } 225b8e80941Smrg return; 226b8e80941Smrg 227b8e80941Smrginvalid_pname: 228b8e80941Smrg _mesa_error(ctx, GL_INVALID_ENUM, "%s(pname=0x%x)", func, pname); 229b8e80941Smrg} 230b8e80941Smrg 231b8e80941Smrgvoid GLAPIENTRY 232b8e80941Smrg_mesa_GetMemoryObjectParameterivEXT(GLuint memoryObject, 233b8e80941Smrg GLenum pname, 234b8e80941Smrg GLint *params) 235b8e80941Smrg{ 236b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 237b8e80941Smrg struct gl_memory_object *memObj; 238b8e80941Smrg 239b8e80941Smrg const char *func = "glMemoryObjectParameterivEXT"; 240b8e80941Smrg 241b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 242b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 243b8e80941Smrg return; 244b8e80941Smrg } 245b8e80941Smrg 246b8e80941Smrg memObj = _mesa_lookup_memory_object(ctx, memoryObject); 247b8e80941Smrg if (!memObj) 248b8e80941Smrg return; 249b8e80941Smrg 250b8e80941Smrg switch (pname) { 251b8e80941Smrg case GL_DEDICATED_MEMORY_OBJECT_EXT: 252b8e80941Smrg *params = (GLint) memObj->Dedicated; 253b8e80941Smrg break; 254b8e80941Smrg case GL_PROTECTED_MEMORY_OBJECT_EXT: 255b8e80941Smrg /* EXT_protected_textures not supported */ 256b8e80941Smrg goto invalid_pname; 257b8e80941Smrg default: 258b8e80941Smrg goto invalid_pname; 259b8e80941Smrg } 260b8e80941Smrg return; 261b8e80941Smrg 262b8e80941Smrginvalid_pname: 263b8e80941Smrg _mesa_error(ctx, GL_INVALID_ENUM, "%s(pname=0x%x)", func, pname); 264b8e80941Smrg} 265b8e80941Smrg 266b8e80941Smrgstatic struct gl_memory_object * 267b8e80941Smrglookup_memory_object_err(struct gl_context *ctx, unsigned memory, 268b8e80941Smrg const char* func) 269b8e80941Smrg{ 270b8e80941Smrg if (memory == 0) { 271b8e80941Smrg _mesa_error(ctx, GL_INVALID_VALUE, "%s(memory=0)", func); 272b8e80941Smrg return NULL; 273b8e80941Smrg } 274b8e80941Smrg 275b8e80941Smrg struct gl_memory_object *memObj = _mesa_lookup_memory_object(ctx, memory); 276b8e80941Smrg if (!memObj) 277b8e80941Smrg return NULL; 278b8e80941Smrg 279b8e80941Smrg if (!memObj->Immutable) { 280b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(no associated memory)", 281b8e80941Smrg func); 282b8e80941Smrg return NULL; 283b8e80941Smrg } 284b8e80941Smrg 285b8e80941Smrg return memObj; 286b8e80941Smrg} 287b8e80941Smrg 288b8e80941Smrg/** 289b8e80941Smrg * Helper used by _mesa_TexStorageMem1/2/3DEXT(). 290b8e80941Smrg */ 291b8e80941Smrgstatic void 292b8e80941Smrgtexstorage_memory(GLuint dims, GLenum target, GLsizei levels, 293b8e80941Smrg GLenum internalFormat, GLsizei width, GLsizei height, 294b8e80941Smrg GLsizei depth, GLuint memory, GLuint64 offset, 295b8e80941Smrg const char *func) 296b8e80941Smrg{ 297b8e80941Smrg struct gl_texture_object *texObj; 298b8e80941Smrg struct gl_memory_object *memObj; 299b8e80941Smrg 300b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 301b8e80941Smrg 302b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 303b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 304b8e80941Smrg return; 305b8e80941Smrg } 306b8e80941Smrg 307b8e80941Smrg texObj = _mesa_get_current_tex_object(ctx, target); 308b8e80941Smrg if (!texObj) 309b8e80941Smrg return; 310b8e80941Smrg 311b8e80941Smrg memObj = lookup_memory_object_err(ctx, memory, func); 312b8e80941Smrg if (!memObj) 313b8e80941Smrg return; 314b8e80941Smrg 315b8e80941Smrg _mesa_texture_storage_memory(ctx, dims, texObj, memObj, target, 316b8e80941Smrg levels, internalFormat, 317b8e80941Smrg width, height, depth, offset, false); 318b8e80941Smrg} 319b8e80941Smrg 320b8e80941Smrgstatic void 321b8e80941Smrgtexstorage_memory_ms(GLuint dims, GLenum target, GLsizei samples, 322b8e80941Smrg GLenum internalFormat, GLsizei width, GLsizei height, 323b8e80941Smrg GLsizei depth, GLboolean fixedSampleLocations, 324b8e80941Smrg GLuint memory, GLuint64 offset, const char* func) 325b8e80941Smrg{ 326b8e80941Smrg struct gl_texture_object *texObj; 327b8e80941Smrg struct gl_memory_object *memObj; 328b8e80941Smrg 329b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 330b8e80941Smrg 331b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 332b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 333b8e80941Smrg return; 334b8e80941Smrg } 335b8e80941Smrg 336b8e80941Smrg texObj = _mesa_get_current_tex_object(ctx, target); 337b8e80941Smrg if (!texObj) 338b8e80941Smrg return; 339b8e80941Smrg 340b8e80941Smrg memObj = lookup_memory_object_err(ctx, memory, func); 341b8e80941Smrg if (!memObj) 342b8e80941Smrg return; 343b8e80941Smrg 344b8e80941Smrg _mesa_texture_storage_ms_memory(ctx, dims, texObj, memObj, target, samples, 345b8e80941Smrg internalFormat, width, height, depth, 346b8e80941Smrg fixedSampleLocations, offset, func); 347b8e80941Smrg} 348b8e80941Smrg 349b8e80941Smrg/** 350b8e80941Smrg * Helper used by _mesa_TextureStorageMem1/2/3DEXT(). 351b8e80941Smrg */ 352b8e80941Smrgstatic void 353b8e80941Smrgtexturestorage_memory(GLuint dims, GLuint texture, GLsizei levels, 354b8e80941Smrg GLenum internalFormat, GLsizei width, GLsizei height, 355b8e80941Smrg GLsizei depth, GLuint memory, GLuint64 offset, 356b8e80941Smrg const char *func) 357b8e80941Smrg{ 358b8e80941Smrg struct gl_texture_object *texObj; 359b8e80941Smrg struct gl_memory_object *memObj; 360b8e80941Smrg 361b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 362b8e80941Smrg 363b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 364b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 365b8e80941Smrg return; 366b8e80941Smrg } 367b8e80941Smrg 368b8e80941Smrg texObj = _mesa_lookup_texture(ctx, texture); 369b8e80941Smrg if (!texObj) 370b8e80941Smrg return; 371b8e80941Smrg 372b8e80941Smrg memObj = lookup_memory_object_err(ctx, memory, func); 373b8e80941Smrg if (!memObj) 374b8e80941Smrg return; 375b8e80941Smrg 376b8e80941Smrg _mesa_texture_storage_memory(ctx, dims, texObj, memObj, texObj->Target, 377b8e80941Smrg levels, internalFormat, 378b8e80941Smrg width, height, depth, offset, true); 379b8e80941Smrg} 380b8e80941Smrg 381b8e80941Smrgstatic void 382b8e80941Smrgtexturestorage_memory_ms(GLuint dims, GLuint texture, GLsizei samples, 383b8e80941Smrg GLenum internalFormat, GLsizei width, GLsizei height, 384b8e80941Smrg GLsizei depth, GLboolean fixedSampleLocations, 385b8e80941Smrg GLuint memory, GLuint64 offset, const char* func) 386b8e80941Smrg{ 387b8e80941Smrg struct gl_texture_object *texObj; 388b8e80941Smrg struct gl_memory_object *memObj; 389b8e80941Smrg 390b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 391b8e80941Smrg 392b8e80941Smrg if (!ctx->Extensions.EXT_memory_object) { 393b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 394b8e80941Smrg return; 395b8e80941Smrg } 396b8e80941Smrg 397b8e80941Smrg texObj = _mesa_lookup_texture(ctx, texture); 398b8e80941Smrg if (!texObj) 399b8e80941Smrg return; 400b8e80941Smrg 401b8e80941Smrg memObj = lookup_memory_object_err(ctx, memory, func); 402b8e80941Smrg if (!memObj) 403b8e80941Smrg return; 404b8e80941Smrg 405b8e80941Smrg _mesa_texture_storage_ms_memory(ctx, dims, texObj, memObj, texObj->Target, 406b8e80941Smrg samples, internalFormat, width, height, 407b8e80941Smrg depth, fixedSampleLocations, offset, func); 408b8e80941Smrg} 409b8e80941Smrg 410b8e80941Smrgvoid GLAPIENTRY 411b8e80941Smrg_mesa_TexStorageMem2DEXT(GLenum target, 412b8e80941Smrg GLsizei levels, 413b8e80941Smrg GLenum internalFormat, 414b8e80941Smrg GLsizei width, 415b8e80941Smrg GLsizei height, 416b8e80941Smrg GLuint memory, 417b8e80941Smrg GLuint64 offset) 418b8e80941Smrg{ 419b8e80941Smrg texstorage_memory(2, target, levels, internalFormat, width, height, 1, 420b8e80941Smrg memory, offset, "glTexStorageMem2DEXT"); 421b8e80941Smrg} 422b8e80941Smrg 423b8e80941Smrgvoid GLAPIENTRY 424b8e80941Smrg_mesa_TexStorageMem2DMultisampleEXT(GLenum target, 425b8e80941Smrg GLsizei samples, 426b8e80941Smrg GLenum internalFormat, 427b8e80941Smrg GLsizei width, 428b8e80941Smrg GLsizei height, 429b8e80941Smrg GLboolean fixedSampleLocations, 430b8e80941Smrg GLuint memory, 431b8e80941Smrg GLuint64 offset) 432b8e80941Smrg{ 433b8e80941Smrg texstorage_memory_ms(2, target, samples, internalFormat, width, height, 1, 434b8e80941Smrg fixedSampleLocations, memory, offset, 435b8e80941Smrg "glTexStorageMem2DMultisampleEXT"); 436b8e80941Smrg} 437b8e80941Smrg 438b8e80941Smrgvoid GLAPIENTRY 439b8e80941Smrg_mesa_TexStorageMem3DEXT(GLenum target, 440b8e80941Smrg GLsizei levels, 441b8e80941Smrg GLenum internalFormat, 442b8e80941Smrg GLsizei width, 443b8e80941Smrg GLsizei height, 444b8e80941Smrg GLsizei depth, 445b8e80941Smrg GLuint memory, 446b8e80941Smrg GLuint64 offset) 447b8e80941Smrg{ 448b8e80941Smrg texstorage_memory(3, target, levels, internalFormat, width, height, depth, 449b8e80941Smrg memory, offset, "glTexStorageMem3DEXT"); 450b8e80941Smrg} 451b8e80941Smrg 452b8e80941Smrgvoid GLAPIENTRY 453b8e80941Smrg_mesa_TexStorageMem3DMultisampleEXT(GLenum target, 454b8e80941Smrg GLsizei samples, 455b8e80941Smrg GLenum internalFormat, 456b8e80941Smrg GLsizei width, 457b8e80941Smrg GLsizei height, 458b8e80941Smrg GLsizei depth, 459b8e80941Smrg GLboolean fixedSampleLocations, 460b8e80941Smrg GLuint memory, 461b8e80941Smrg GLuint64 offset) 462b8e80941Smrg{ 463b8e80941Smrg texstorage_memory_ms(3, target, samples, internalFormat, width, height, 464b8e80941Smrg depth, fixedSampleLocations, memory, offset, 465b8e80941Smrg "glTexStorageMem3DMultisampleEXT"); 466b8e80941Smrg} 467b8e80941Smrg 468b8e80941Smrgvoid GLAPIENTRY 469b8e80941Smrg_mesa_TextureStorageMem2DEXT(GLuint texture, 470b8e80941Smrg GLsizei levels, 471b8e80941Smrg GLenum internalFormat, 472b8e80941Smrg GLsizei width, 473b8e80941Smrg GLsizei height, 474b8e80941Smrg GLuint memory, 475b8e80941Smrg GLuint64 offset) 476b8e80941Smrg{ 477b8e80941Smrg texturestorage_memory(2, texture, levels, internalFormat, width, height, 1, 478b8e80941Smrg memory, offset, "glTexureStorageMem2DEXT"); 479b8e80941Smrg} 480b8e80941Smrg 481b8e80941Smrgvoid GLAPIENTRY 482b8e80941Smrg_mesa_TextureStorageMem2DMultisampleEXT(GLuint texture, 483b8e80941Smrg GLsizei samples, 484b8e80941Smrg GLenum internalFormat, 485b8e80941Smrg GLsizei width, 486b8e80941Smrg GLsizei height, 487b8e80941Smrg GLboolean fixedSampleLocations, 488b8e80941Smrg GLuint memory, 489b8e80941Smrg GLuint64 offset) 490b8e80941Smrg{ 491b8e80941Smrg texturestorage_memory_ms(2, texture, samples, internalFormat, width, height, 492b8e80941Smrg 1, fixedSampleLocations, memory, offset, 493b8e80941Smrg "glTextureStorageMem2DMultisampleEXT"); 494b8e80941Smrg} 495b8e80941Smrg 496b8e80941Smrgvoid GLAPIENTRY 497b8e80941Smrg_mesa_TextureStorageMem3DEXT(GLuint texture, 498b8e80941Smrg GLsizei levels, 499b8e80941Smrg GLenum internalFormat, 500b8e80941Smrg GLsizei width, 501b8e80941Smrg GLsizei height, 502b8e80941Smrg GLsizei depth, 503b8e80941Smrg GLuint memory, 504b8e80941Smrg GLuint64 offset) 505b8e80941Smrg{ 506b8e80941Smrg texturestorage_memory(3, texture, levels, internalFormat, width, height, 507b8e80941Smrg depth, memory, offset, "glTextureStorageMem3DEXT"); 508b8e80941Smrg} 509b8e80941Smrg 510b8e80941Smrgvoid GLAPIENTRY 511b8e80941Smrg_mesa_TextureStorageMem3DMultisampleEXT(GLuint texture, 512b8e80941Smrg GLsizei samples, 513b8e80941Smrg GLenum internalFormat, 514b8e80941Smrg GLsizei width, 515b8e80941Smrg GLsizei height, 516b8e80941Smrg GLsizei depth, 517b8e80941Smrg GLboolean fixedSampleLocations, 518b8e80941Smrg GLuint memory, 519b8e80941Smrg GLuint64 offset) 520b8e80941Smrg{ 521b8e80941Smrg texturestorage_memory_ms(3, texture, samples, internalFormat, width, height, 522b8e80941Smrg depth, fixedSampleLocations, memory, offset, 523b8e80941Smrg "glTextureStorageMem3DMultisampleEXT"); 524b8e80941Smrg} 525b8e80941Smrg 526b8e80941Smrgvoid GLAPIENTRY 527b8e80941Smrg_mesa_TexStorageMem1DEXT(GLenum target, 528b8e80941Smrg GLsizei levels, 529b8e80941Smrg GLenum internalFormat, 530b8e80941Smrg GLsizei width, 531b8e80941Smrg GLuint memory, 532b8e80941Smrg GLuint64 offset) 533b8e80941Smrg{ 534b8e80941Smrg texstorage_memory(1, target, levels, internalFormat, width, 1, 1, memory, 535b8e80941Smrg offset, "glTexStorageMem1DEXT"); 536b8e80941Smrg} 537b8e80941Smrg 538b8e80941Smrgvoid GLAPIENTRY 539b8e80941Smrg_mesa_TextureStorageMem1DEXT(GLuint texture, 540b8e80941Smrg GLsizei levels, 541b8e80941Smrg GLenum internalFormat, 542b8e80941Smrg GLsizei width, 543b8e80941Smrg GLuint memory, 544b8e80941Smrg GLuint64 offset) 545b8e80941Smrg{ 546b8e80941Smrg texturestorage_memory(1, texture, levels, internalFormat, width, 1, 1, 547b8e80941Smrg memory, offset, "glTextureStorageMem1DEXT"); 548b8e80941Smrg} 549b8e80941Smrg 550b8e80941Smrg/** 551b8e80941Smrg * Used as a placeholder for semaphore objects between glGenSemaphoresEXT() 552b8e80941Smrg * and glImportSemaphoreFdEXT(), so that glIsSemaphoreEXT() can work correctly. 553b8e80941Smrg */ 554b8e80941Smrgstatic struct gl_semaphore_object DummySemaphoreObject; 555b8e80941Smrg 556b8e80941Smrg/** 557b8e80941Smrg * Delete a semaphore object. Called via ctx->Driver.DeleteSemaphore(). 558b8e80941Smrg * Not removed from hash table here. 559b8e80941Smrg */ 560b8e80941Smrgvoid 561b8e80941Smrg_mesa_delete_semaphore_object(struct gl_context *ctx, 562b8e80941Smrg struct gl_semaphore_object *semObj) 563b8e80941Smrg{ 564b8e80941Smrg if (semObj != &DummySemaphoreObject) 565b8e80941Smrg free(semObj); 566b8e80941Smrg} 567b8e80941Smrg 568b8e80941Smrg/** 569b8e80941Smrg * Initialize a semaphore object to default values. 570b8e80941Smrg */ 571b8e80941Smrgvoid 572b8e80941Smrg_mesa_initialize_semaphore_object(struct gl_context *ctx, 573b8e80941Smrg struct gl_semaphore_object *obj, 574b8e80941Smrg GLuint name) 575b8e80941Smrg{ 576b8e80941Smrg memset(obj, 0, sizeof(struct gl_semaphore_object)); 577b8e80941Smrg obj->Name = name; 578b8e80941Smrg} 579b8e80941Smrg 580b8e80941Smrgvoid GLAPIENTRY 581b8e80941Smrg_mesa_GenSemaphoresEXT(GLsizei n, GLuint *semaphores) 582b8e80941Smrg{ 583b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 584b8e80941Smrg 585b8e80941Smrg const char *func = "glGenSemaphoresEXT"; 586b8e80941Smrg 587b8e80941Smrg if (MESA_VERBOSE & (VERBOSE_API)) 588b8e80941Smrg _mesa_debug(ctx, "%s(%d, %p)", func, n, semaphores); 589b8e80941Smrg 590b8e80941Smrg if (!ctx->Extensions.EXT_semaphore) { 591b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 592b8e80941Smrg return; 593b8e80941Smrg } 594b8e80941Smrg 595b8e80941Smrg if (n < 0) { 596b8e80941Smrg _mesa_error(ctx, GL_INVALID_VALUE, "%s(n < 0)", func); 597b8e80941Smrg return; 598b8e80941Smrg } 599b8e80941Smrg 600b8e80941Smrg if (!semaphores) 601b8e80941Smrg return; 602b8e80941Smrg 603b8e80941Smrg _mesa_HashLockMutex(ctx->Shared->SemaphoreObjects); 604b8e80941Smrg GLuint first = _mesa_HashFindFreeKeyBlock(ctx->Shared->SemaphoreObjects, n); 605b8e80941Smrg if (first) { 606b8e80941Smrg for (GLsizei i = 0; i < n; i++) { 607b8e80941Smrg semaphores[i] = first + i; 608b8e80941Smrg _mesa_HashInsertLocked(ctx->Shared->SemaphoreObjects, 609b8e80941Smrg semaphores[i], &DummySemaphoreObject); 610b8e80941Smrg } 611b8e80941Smrg } 612b8e80941Smrg 613b8e80941Smrg _mesa_HashUnlockMutex(ctx->Shared->SemaphoreObjects); 614b8e80941Smrg} 615b8e80941Smrg 616b8e80941Smrgvoid GLAPIENTRY 617b8e80941Smrg_mesa_DeleteSemaphoresEXT(GLsizei n, const GLuint *semaphores) 618b8e80941Smrg{ 619b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 620b8e80941Smrg 621b8e80941Smrg const char *func = "glDeleteSemaphoresEXT"; 622b8e80941Smrg 623b8e80941Smrg if (MESA_VERBOSE & (VERBOSE_API)) { 624b8e80941Smrg _mesa_debug(ctx, "%s(%d, %p)\n", func, n, semaphores); 625b8e80941Smrg } 626b8e80941Smrg 627b8e80941Smrg if (!ctx->Extensions.EXT_semaphore) { 628b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 629b8e80941Smrg return; 630b8e80941Smrg } 631b8e80941Smrg 632b8e80941Smrg if (n < 0) { 633b8e80941Smrg _mesa_error(ctx, GL_INVALID_VALUE, "%s(n < 0)", func); 634b8e80941Smrg return; 635b8e80941Smrg } 636b8e80941Smrg 637b8e80941Smrg if (!semaphores) 638b8e80941Smrg return; 639b8e80941Smrg 640b8e80941Smrg _mesa_HashLockMutex(ctx->Shared->SemaphoreObjects); 641b8e80941Smrg for (GLint i = 0; i < n; i++) { 642b8e80941Smrg if (semaphores[i] > 0) { 643b8e80941Smrg struct gl_semaphore_object *delObj 644b8e80941Smrg = _mesa_lookup_semaphore_object_locked(ctx, semaphores[i]); 645b8e80941Smrg 646b8e80941Smrg if (delObj) { 647b8e80941Smrg _mesa_HashRemoveLocked(ctx->Shared->SemaphoreObjects, 648b8e80941Smrg semaphores[i]); 649b8e80941Smrg ctx->Driver.DeleteSemaphoreObject(ctx, delObj); 650b8e80941Smrg } 651b8e80941Smrg } 652b8e80941Smrg } 653b8e80941Smrg _mesa_HashUnlockMutex(ctx->Shared->SemaphoreObjects); 654b8e80941Smrg} 655b8e80941Smrg 656b8e80941SmrgGLboolean GLAPIENTRY 657b8e80941Smrg_mesa_IsSemaphoreEXT(GLuint semaphore) 658b8e80941Smrg{ 659b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 660b8e80941Smrg 661b8e80941Smrg if (!ctx->Extensions.EXT_semaphore) { 662b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "glIsSemaphoreEXT(unsupported)"); 663b8e80941Smrg return GL_FALSE; 664b8e80941Smrg } 665b8e80941Smrg 666b8e80941Smrg struct gl_semaphore_object *obj = 667b8e80941Smrg _mesa_lookup_semaphore_object(ctx, semaphore); 668b8e80941Smrg 669b8e80941Smrg return obj ? GL_TRUE : GL_FALSE; 670b8e80941Smrg} 671b8e80941Smrg 672b8e80941Smrg/** 673b8e80941Smrg * Helper that outputs the correct error status for parameter 674b8e80941Smrg * calls where no pnames are defined 675b8e80941Smrg */ 676b8e80941Smrgstatic void 677b8e80941Smrgsemaphore_parameter_stub(const char* func, GLenum pname) 678b8e80941Smrg{ 679b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 680b8e80941Smrg 681b8e80941Smrg if (!ctx->Extensions.EXT_semaphore) { 682b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 683b8e80941Smrg return; 684b8e80941Smrg } 685b8e80941Smrg 686b8e80941Smrg /* EXT_semaphore and EXT_semaphore_fd define no parameters */ 687b8e80941Smrg _mesa_error(ctx, GL_INVALID_ENUM, "%s(pname=0x%x)", func, pname); 688b8e80941Smrg} 689b8e80941Smrg 690b8e80941Smrgvoid GLAPIENTRY 691b8e80941Smrg_mesa_SemaphoreParameterui64vEXT(GLuint semaphore, 692b8e80941Smrg GLenum pname, 693b8e80941Smrg const GLuint64 *params) 694b8e80941Smrg{ 695b8e80941Smrg const char *func = "glSemaphoreParameterui64vEXT"; 696b8e80941Smrg 697b8e80941Smrg semaphore_parameter_stub(func, pname); 698b8e80941Smrg} 699b8e80941Smrg 700b8e80941Smrgvoid GLAPIENTRY 701b8e80941Smrg_mesa_GetSemaphoreParameterui64vEXT(GLuint semaphore, 702b8e80941Smrg GLenum pname, 703b8e80941Smrg GLuint64 *params) 704b8e80941Smrg{ 705b8e80941Smrg const char *func = "glGetSemaphoreParameterui64vEXT"; 706b8e80941Smrg 707b8e80941Smrg semaphore_parameter_stub(func, pname); 708b8e80941Smrg} 709b8e80941Smrg 710b8e80941Smrgvoid GLAPIENTRY 711b8e80941Smrg_mesa_WaitSemaphoreEXT(GLuint semaphore, 712b8e80941Smrg GLuint numBufferBarriers, 713b8e80941Smrg const GLuint *buffers, 714b8e80941Smrg GLuint numTextureBarriers, 715b8e80941Smrg const GLuint *textures, 716b8e80941Smrg const GLenum *srcLayouts) 717b8e80941Smrg{ 718b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 719b8e80941Smrg struct gl_semaphore_object *semObj = NULL; 720b8e80941Smrg struct gl_buffer_object **bufObjs = NULL; 721b8e80941Smrg struct gl_texture_object **texObjs = NULL; 722b8e80941Smrg 723b8e80941Smrg const char *func = "glWaitSemaphoreEXT"; 724b8e80941Smrg 725b8e80941Smrg if (!ctx->Extensions.EXT_semaphore) { 726b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 727b8e80941Smrg return; 728b8e80941Smrg } 729b8e80941Smrg 730b8e80941Smrg ASSERT_OUTSIDE_BEGIN_END(ctx); 731b8e80941Smrg 732b8e80941Smrg semObj = _mesa_lookup_semaphore_object(ctx, semaphore); 733b8e80941Smrg if (!semObj) 734b8e80941Smrg return; 735b8e80941Smrg 736b8e80941Smrg FLUSH_VERTICES(ctx, 0); 737b8e80941Smrg FLUSH_CURRENT(ctx, 0); 738b8e80941Smrg 739b8e80941Smrg bufObjs = malloc(sizeof(struct gl_buffer_object *) * numBufferBarriers); 740b8e80941Smrg if (!bufObjs) { 741b8e80941Smrg _mesa_error(ctx, GL_OUT_OF_MEMORY, "%s(numBufferBarriers=%u)", 742b8e80941Smrg func, numBufferBarriers); 743b8e80941Smrg goto end; 744b8e80941Smrg } 745b8e80941Smrg 746b8e80941Smrg for (unsigned i = 0; i < numBufferBarriers; i++) { 747b8e80941Smrg bufObjs[i] = _mesa_lookup_bufferobj(ctx, buffers[i]); 748b8e80941Smrg } 749b8e80941Smrg 750b8e80941Smrg texObjs = malloc(sizeof(struct gl_texture_object *) * numTextureBarriers); 751b8e80941Smrg if (!texObjs) { 752b8e80941Smrg _mesa_error(ctx, GL_OUT_OF_MEMORY, "%s(numTextureBarriers=%u)", 753b8e80941Smrg func, numTextureBarriers); 754b8e80941Smrg goto end; 755b8e80941Smrg } 756b8e80941Smrg 757b8e80941Smrg for (unsigned i = 0; i < numTextureBarriers; i++) { 758b8e80941Smrg texObjs[i] = _mesa_lookup_texture(ctx, textures[i]); 759b8e80941Smrg } 760b8e80941Smrg 761b8e80941Smrg ctx->Driver.ServerWaitSemaphoreObject(ctx, semObj, 762b8e80941Smrg numBufferBarriers, bufObjs, 763b8e80941Smrg numTextureBarriers, texObjs, 764b8e80941Smrg srcLayouts); 765b8e80941Smrg 766b8e80941Smrgend: 767b8e80941Smrg free(bufObjs); 768b8e80941Smrg free(texObjs); 769b8e80941Smrg} 770b8e80941Smrg 771b8e80941Smrgvoid GLAPIENTRY 772b8e80941Smrg_mesa_SignalSemaphoreEXT(GLuint semaphore, 773b8e80941Smrg GLuint numBufferBarriers, 774b8e80941Smrg const GLuint *buffers, 775b8e80941Smrg GLuint numTextureBarriers, 776b8e80941Smrg const GLuint *textures, 777b8e80941Smrg const GLenum *dstLayouts) 778b8e80941Smrg{ 779b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 780b8e80941Smrg struct gl_semaphore_object *semObj = NULL; 781b8e80941Smrg struct gl_buffer_object **bufObjs = NULL; 782b8e80941Smrg struct gl_texture_object **texObjs = NULL; 783b8e80941Smrg 784b8e80941Smrg const char *func = "glSignalSemaphoreEXT"; 785b8e80941Smrg 786b8e80941Smrg if (!ctx->Extensions.EXT_semaphore) { 787b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 788b8e80941Smrg return; 789b8e80941Smrg } 790b8e80941Smrg 791b8e80941Smrg ASSERT_OUTSIDE_BEGIN_END(ctx); 792b8e80941Smrg 793b8e80941Smrg semObj = _mesa_lookup_semaphore_object(ctx, semaphore); 794b8e80941Smrg if (!semObj) 795b8e80941Smrg return; 796b8e80941Smrg 797b8e80941Smrg FLUSH_VERTICES(ctx, 0); 798b8e80941Smrg FLUSH_CURRENT(ctx, 0); 799b8e80941Smrg 800b8e80941Smrg bufObjs = malloc(sizeof(struct gl_buffer_object *) * numBufferBarriers); 801b8e80941Smrg if (!bufObjs) { 802b8e80941Smrg _mesa_error(ctx, GL_OUT_OF_MEMORY, "%s(numBufferBarriers=%u)", 803b8e80941Smrg func, numBufferBarriers); 804b8e80941Smrg goto end; 805b8e80941Smrg } 806b8e80941Smrg 807b8e80941Smrg for (unsigned i = 0; i < numBufferBarriers; i++) { 808b8e80941Smrg bufObjs[i] = _mesa_lookup_bufferobj(ctx, buffers[i]); 809b8e80941Smrg } 810b8e80941Smrg 811b8e80941Smrg texObjs = malloc(sizeof(struct gl_texture_object *) * numTextureBarriers); 812b8e80941Smrg if (!texObjs) { 813b8e80941Smrg _mesa_error(ctx, GL_OUT_OF_MEMORY, "%s(numTextureBarriers=%u)", 814b8e80941Smrg func, numTextureBarriers); 815b8e80941Smrg goto end; 816b8e80941Smrg } 817b8e80941Smrg 818b8e80941Smrg for (unsigned i = 0; i < numTextureBarriers; i++) { 819b8e80941Smrg texObjs[i] = _mesa_lookup_texture(ctx, textures[i]); 820b8e80941Smrg } 821b8e80941Smrg 822b8e80941Smrg ctx->Driver.ServerSignalSemaphoreObject(ctx, semObj, 823b8e80941Smrg numBufferBarriers, bufObjs, 824b8e80941Smrg numTextureBarriers, texObjs, 825b8e80941Smrg dstLayouts); 826b8e80941Smrg 827b8e80941Smrgend: 828b8e80941Smrg free(bufObjs); 829b8e80941Smrg free(texObjs); 830b8e80941Smrg} 831b8e80941Smrg 832b8e80941Smrgvoid GLAPIENTRY 833b8e80941Smrg_mesa_ImportMemoryFdEXT(GLuint memory, 834b8e80941Smrg GLuint64 size, 835b8e80941Smrg GLenum handleType, 836b8e80941Smrg GLint fd) 837b8e80941Smrg{ 838b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 839b8e80941Smrg 840b8e80941Smrg const char *func = "glImportMemoryFdEXT"; 841b8e80941Smrg 842b8e80941Smrg if (!ctx->Extensions.EXT_memory_object_fd) { 843b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 844b8e80941Smrg return; 845b8e80941Smrg } 846b8e80941Smrg 847b8e80941Smrg if (handleType != GL_HANDLE_TYPE_OPAQUE_FD_EXT) { 848b8e80941Smrg _mesa_error(ctx, GL_INVALID_ENUM, "%s(handleType=%u)", func, handleType); 849b8e80941Smrg return; 850b8e80941Smrg } 851b8e80941Smrg 852b8e80941Smrg struct gl_memory_object *memObj = _mesa_lookup_memory_object(ctx, memory); 853b8e80941Smrg if (!memObj) 854b8e80941Smrg return; 855b8e80941Smrg 856b8e80941Smrg ctx->Driver.ImportMemoryObjectFd(ctx, memObj, size, fd); 857b8e80941Smrg memObj->Immutable = GL_TRUE; 858b8e80941Smrg} 859b8e80941Smrg 860b8e80941Smrgvoid GLAPIENTRY 861b8e80941Smrg_mesa_ImportSemaphoreFdEXT(GLuint semaphore, 862b8e80941Smrg GLenum handleType, 863b8e80941Smrg GLint fd) 864b8e80941Smrg{ 865b8e80941Smrg GET_CURRENT_CONTEXT(ctx); 866b8e80941Smrg 867b8e80941Smrg const char *func = "glImportSemaphoreFdEXT"; 868b8e80941Smrg 869b8e80941Smrg if (!ctx->Extensions.EXT_semaphore_fd) { 870b8e80941Smrg _mesa_error(ctx, GL_INVALID_OPERATION, "%s(unsupported)", func); 871b8e80941Smrg return; 872b8e80941Smrg } 873b8e80941Smrg 874b8e80941Smrg if (handleType != GL_HANDLE_TYPE_OPAQUE_FD_EXT) { 875b8e80941Smrg _mesa_error(ctx, GL_INVALID_ENUM, "%s(handleType=%u)", func, handleType); 876b8e80941Smrg return; 877b8e80941Smrg } 878b8e80941Smrg 879b8e80941Smrg struct gl_semaphore_object *semObj = _mesa_lookup_semaphore_object(ctx, 880b8e80941Smrg semaphore); 881b8e80941Smrg if (!semObj) 882b8e80941Smrg return; 883b8e80941Smrg 884b8e80941Smrg if (semObj == &DummySemaphoreObject) { 885b8e80941Smrg semObj = ctx->Driver.NewSemaphoreObject(ctx, semaphore); 886b8e80941Smrg if (!semObj) { 887b8e80941Smrg _mesa_error(ctx, GL_OUT_OF_MEMORY, "%s", func); 888b8e80941Smrg return; 889b8e80941Smrg } 890b8e80941Smrg _mesa_HashInsert(ctx->Shared->SemaphoreObjects, semaphore, semObj); 891b8e80941Smrg } 892b8e80941Smrg 893b8e80941Smrg ctx->Driver.ImportSemaphoreFd(ctx, semObj, fd); 894b8e80941Smrg} 895