Stefan Dösinger : wined3d: Use glMapBuffer for 1: 1 uploads in PreLoad.

Alexandre Julliard julliard at winehq.org
Tue Mar 16 11:49:21 CDT 2010


Module: wine
Branch: master
Commit: 1691a6d7d0d763ccfda489a44fa3a1e7df223ad1
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=1691a6d7d0d763ccfda489a44fa3a1e7df223ad1

Author: Stefan Dösinger <stefan at codeweavers.com>
Date:   Thu Mar 11 12:23:19 2010 +0100

wined3d: Use glMapBuffer for 1:1 uploads in PreLoad.

This is needed to take advantage of asynchronous uploads with double buffered buffers

---

 dlls/wined3d/buffer.c |   66 ++++++++++++++++++++++++++++++++++++++++---------
 1 files changed, 54 insertions(+), 12 deletions(-)

diff --git a/dlls/wined3d/buffer.c b/dlls/wined3d/buffer.c
index 86d6fb4..37c3feb 100644
--- a/dlls/wined3d/buffer.c
+++ b/dlls/wined3d/buffer.c
@@ -766,6 +766,59 @@ static DWORD STDMETHODCALLTYPE buffer_GetPriority(IWineD3DBuffer *iface)
     return resource_get_priority((IWineD3DResource *)iface);
 }
 
+/* The caller provides a GL context */
+static void buffer_direct_upload(struct wined3d_buffer *This, const struct wined3d_gl_info *gl_info)
+{
+        BYTE *map;
+        UINT start = 0, len = 0;
+
+        ENTER_GL();
+        GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
+        checkGLcall("glBindBufferARB");
+        if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
+        {
+            GLbitfield mapflags;
+            mapflags = GL_MAP_WRITE_BIT | GL_MAP_FLUSH_EXPLICIT_BIT;
+            map = GL_EXTCALL(glMapBufferRange(This->buffer_type_hint, 0,
+                                              This->resource.size, mapflags));
+            checkGLcall("glMapBufferRange");
+        }
+        else
+        {
+            map = GL_EXTCALL(glMapBufferARB(This->buffer_type_hint, GL_WRITE_ONLY_ARB));
+            checkGLcall("glMapBufferARB");
+        }
+        if (!map)
+        {
+            LEAVE_GL();
+            ERR("Failed to map opengl buffer\n");
+            return;
+        }
+
+        while(This->modified_areas)
+        {
+            This->modified_areas--;
+            start = This->maps[This->modified_areas].offset;
+            len = This->maps[This->modified_areas].size;
+
+            memcpy(map + start, This->resource.allocatedMemory + start, len);
+
+            if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
+            {
+                GL_EXTCALL(glFlushMappedBufferRange(This->buffer_type_hint, start, len));
+                checkGLcall("glFlushMappedBufferRange");
+            }
+            else if (This->flags & WINED3D_BUFFER_FLUSH)
+            {
+                GL_EXTCALL(glFlushMappedBufferRangeAPPLE(This->buffer_type_hint, start, len));
+                checkGLcall("glFlushMappedBufferRangeAPPLE");
+            }
+        }
+        GL_EXTCALL(glUnmapBufferARB(This->buffer_type_hint));
+        checkGLcall("glUnmapBufferARB");
+        LEAVE_GL();
+}
+
 static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
 {
     struct wined3d_buffer *This = (struct wined3d_buffer *)iface;
@@ -896,18 +949,7 @@ static void STDMETHODCALLTYPE buffer_PreLoad(IWineD3DBuffer *iface)
             return;
         }
 
-        ENTER_GL();
-        GL_EXTCALL(glBindBufferARB(This->buffer_type_hint, This->buffer_object));
-        checkGLcall("glBindBufferARB");
-        while(This->modified_areas)
-        {
-            This->modified_areas--;
-            start = This->maps[This->modified_areas].offset;
-            len = This->maps[This->modified_areas].size;
-            GL_EXTCALL(glBufferSubDataARB(This->buffer_type_hint, start, len, This->resource.allocatedMemory + start));
-            checkGLcall("glBufferSubDataARB");
-        }
-        LEAVE_GL();
+        buffer_direct_upload(This, context->gl_info);
 
         context_release(context);
         return;




More information about the wine-cvs mailing list