mesa: hook up (Named)BufferStorageMem api
authorTimothy Arceri <tarceri@itsqueeze.com>
Wed, 26 Jul 2017 06:50:44 +0000 (16:50 +1000)
committerTimothy Arceri <tarceri@itsqueeze.com>
Sun, 6 Aug 2017 02:42:06 +0000 (12:42 +1000)
Include no_error variants as well.

v2 (Timothy Arceri):
 - reduced code churn by squashing some changes into
   previous commits

v3 (Timothy Arceri):
 - drop unused function declaration

v4 (Timothy Arceri):
 - fix Driver function assert()
 - add missing GL errors

Signed-off-by: Andres Rodriguez <andresx7@gmail.com>
Reviewed-by: Samuel Pitoiset <samuel.pitoiset@gmail.com>
src/mesa/main/bufferobj.c

index 05c15661b29a0e431f0da82d87935b0ccb967f7e..625fd5f3423ccedf7bf19cec5acaa8ef380b7e12 100644 (file)
@@ -39,6 +39,7 @@
 #include "imports.h"
 #include "context.h"
 #include "bufferobj.h"
+#include "externalobjects.h"
 #include "mtypes.h"
 #include "teximage.h"
 #include "glformats.h"
@@ -1820,9 +1821,12 @@ validate_buffer_storage(struct gl_context *ctx,
 
 static void
 buffer_storage(struct gl_context *ctx, struct gl_buffer_object *bufObj,
-               GLenum target, GLsizeiptr size, const GLvoid *data,
-               GLbitfield flags, const char *func)
+               struct gl_memory_object *memObj, GLenum target,
+               GLsizeiptr size, const GLvoid *data, GLbitfield flags,
+               GLuint64 offset, const char *func)
 {
+   GLboolean res;
+
    /* Unmap the existing buffer.  We'll replace it now.  Not an error. */
    _mesa_buffer_unmap_all_mappings(ctx, bufObj);
 
@@ -1832,9 +1836,18 @@ buffer_storage(struct gl_context *ctx, struct gl_buffer_object *bufObj,
    bufObj->Immutable = GL_TRUE;
    bufObj->MinMaxCacheDirty = true;
 
-   assert(ctx->Driver.BufferData);
-   if (!ctx->Driver.BufferData(ctx, target, size, data, GL_DYNAMIC_DRAW,
-                               flags, bufObj)) {
+   if (memObj) {
+      assert(ctx->Driver.BufferDataMem);
+      res = ctx->Driver.BufferDataMem(ctx, target, size, memObj, offset,
+                                      GL_DYNAMIC_DRAW, bufObj);
+   }
+   else {
+      assert(ctx->Driver.BufferData);
+      res = ctx->Driver.BufferData(ctx, target, size, data, GL_DYNAMIC_DRAW,
+                                   flags, bufObj);
+   }
+
+   if (!res) {
       if (target == GL_EXTERNAL_VIRTUAL_MEMORY_BUFFER_AMD) {
          /* Even though the interaction between AMD_pinned_memory and
           * glBufferStorage is not described in the spec, Graham Sellers
@@ -1851,11 +1864,39 @@ buffer_storage(struct gl_context *ctx, struct gl_buffer_object *bufObj,
 
 static ALWAYS_INLINE void
 inlined_buffer_storage(GLenum target, GLuint buffer, GLsizeiptr size,
-                       const GLvoid *data, GLbitfield flags, bool dsa,
-                       bool no_error, const char *func)
+                       const GLvoid *data, GLbitfield flags,
+                       GLuint memory, GLuint64 offset,
+                       bool dsa, bool mem, bool no_error, const char *func)
 {
    GET_CURRENT_CONTEXT(ctx);
    struct gl_buffer_object *bufObj;
+   struct gl_memory_object *memObj = NULL;
+
+   if (mem) {
+      /* From the EXT_external_objects spec:
+       *
+       *   "An INVALID_VALUE error is generated by BufferStorageMemEXT and
+       *   NamedBufferStorageMemEXT if <memory> is 0, or ..."
+       */
+      if (!no_error && memory == 0) {
+         _mesa_error(ctx, GL_INVALID_VALUE, "%s(memory == 0)", func);
+      }
+
+      memObj = _mesa_lookup_memory_object(ctx, memory);
+      if (!memObj)
+         return;
+
+      /* From the EXT_external_objects spec:
+       *
+       *   "An INVALID_OPERATION error is generated if <memory> names a
+       *   valid memory object which has no associated memory."
+       */
+      if (!no_error && !memObj->Immutable) {
+         _mesa_error(ctx, GL_INVALID_OPERATION, "%s(no associated memory)",
+                     func);
+         return;
+      }
+   }
 
    if (dsa) {
       if (no_error) {
@@ -1877,7 +1918,7 @@ inlined_buffer_storage(GLenum target, GLuint buffer, GLsizeiptr size,
    }
 
    if (no_error || validate_buffer_storage(ctx, bufObj, size, flags, func))
-      buffer_storage(ctx, bufObj, target, size, data, flags, func);
+      buffer_storage(ctx, bufObj, memObj, target, size, data, flags, offset, func);
 }
 
 
@@ -1885,8 +1926,8 @@ void GLAPIENTRY
 _mesa_BufferStorage_no_error(GLenum target, GLsizeiptr size,
                              const GLvoid *data, GLbitfield flags)
 {
-   inlined_buffer_storage(target, 0, size, data, flags, false, true,
-                          "glBufferStorage");
+   inlined_buffer_storage(target, 0, size, data, flags, GL_NONE, 0,
+                          false, false, true, "glBufferStorage");
 }
 
 
@@ -1894,8 +1935,8 @@ void GLAPIENTRY
 _mesa_BufferStorage(GLenum target, GLsizeiptr size, const GLvoid *data,
                     GLbitfield flags)
 {
-   inlined_buffer_storage(target, 0, size, data, flags, false, false,
-                          "glBufferStorage");
+   inlined_buffer_storage(target, 0, size, data, flags, GL_NONE, 0,
+                          false, false, false, "glBufferStorage");
 }
 
 
@@ -1903,7 +1944,8 @@ void GLAPIENTRY
 _mesa_BufferStorageMemEXT(GLenum target, GLsizeiptr size,
                           GLuint memory, GLuint64 offset)
 {
-
+   inlined_buffer_storage(target, 0, size, NULL, 0, memory, offset,
+                          false, true, false, "glBufferStorageMemEXT");
 }
 
 
@@ -1911,7 +1953,8 @@ void GLAPIENTRY
 _mesa_BufferStorageMemEXT_no_error(GLenum target, GLsizeiptr size,
                                    GLuint memory, GLuint64 offset)
 {
-
+   inlined_buffer_storage(target, 0, size, NULL, 0, memory, offset,
+                          false, true, true, "glBufferStorageMemEXT");
 }
 
 
@@ -1922,8 +1965,8 @@ _mesa_NamedBufferStorage_no_error(GLuint buffer, GLsizeiptr size,
    /* In direct state access, buffer objects have an unspecified target
     * since they are not required to be bound.
     */
-   inlined_buffer_storage(GL_NONE, buffer, size, data, flags, true, true,
-                          "glNamedBufferStorage");
+   inlined_buffer_storage(GL_NONE, buffer, size, data, flags, GL_NONE, 0,
+                          true, false, true, "glNamedBufferStorage");
 }
 
 
@@ -1934,15 +1977,16 @@ _mesa_NamedBufferStorage(GLuint buffer, GLsizeiptr size, const GLvoid *data,
    /* In direct state access, buffer objects have an unspecified target
     * since they are not required to be bound.
     */
-   inlined_buffer_storage(GL_NONE, buffer, size, data, flags, true, false,
-                          "glNamedBufferStorage");
+   inlined_buffer_storage(GL_NONE, buffer, size, data, flags, GL_NONE, 0,
+                          true, false, false, "glNamedBufferStorage");
 }
 
 void GLAPIENTRY
 _mesa_NamedBufferStorageMemEXT(GLuint buffer, GLsizeiptr size,
                                GLuint memory, GLuint64 offset)
 {
-
+   inlined_buffer_storage(GL_NONE, buffer, size, GL_NONE, 0, memory, offset,
+                          true, true, false, "glNamedBufferStorageMemEXT");
 }
 
 
@@ -1950,7 +1994,8 @@ void GLAPIENTRY
 _mesa_NamedBufferStorageMemEXT_no_error(GLuint buffer, GLsizeiptr size,
                                         GLuint memory, GLuint64 offset)
 {
-
+   inlined_buffer_storage(GL_NONE, buffer, size, GL_NONE, 0, memory, offset,
+                          true, true, true, "glNamedBufferStorageMemEXT");
 }