Signed-off-by: Zebediah Figura zfigura@codeweavers.com --- dlls/wined3d/adapter_gl.c | 23 ++++++++ dlls/wined3d/adapter_vk.c | 10 ++++ dlls/wined3d/buffer.c | 98 ++++------------------------------ dlls/wined3d/directx.c | 5 ++ dlls/wined3d/wined3d_private.h | 13 ++++- 5 files changed, 59 insertions(+), 90 deletions(-)
diff --git a/dlls/wined3d/adapter_gl.c b/dlls/wined3d/adapter_gl.c index f1cdbffe718..86fe40aa73f 100644 --- a/dlls/wined3d/adapter_gl.c +++ b/dlls/wined3d/adapter_gl.c @@ -4604,6 +4604,28 @@ static void adapter_gl_flush_bo_address(struct wined3d_context *context, wined3d_context_gl_flush_bo_address(wined3d_context_gl(context), data, size); }
+static void adapter_gl_destroy_bo(struct wined3d_context *context, struct wined3d_bo *bo) +{ + struct wined3d_context_gl *context_gl = wined3d_context_gl(context); + struct wined3d_bo_gl *bo_gl = wined3d_bo_gl(bo); + + if (context_gl->c.transform_feedback_active && bo_gl->binding == GL_TRANSFORM_FEEDBACK_BUFFER + && wined3d_context_is_graphics_state_dirty(&context_gl->c, STATE_STREAM_OUTPUT)) + { + /* It's illegal to (un)bind GL_TRANSFORM_FEEDBACK_BUFFER while transform + * feedback is active. Deleting a buffer implicitly unbinds it, so we + * need to end transform feedback here if this buffer was bound. + * + * This should only be possible if STATE_STREAM_OUTPUT is dirty; if we + * do a draw call before destroying this buffer then the draw call will + * already rebind the GL target. */ + WARN("Deleting buffer object %p, disabling transform feedback.\n", bo_gl); + wined3d_context_gl_end_transform_feedback(context_gl); + } + + wined3d_context_gl_destroy_bo(context_gl, bo_gl); +} + static HRESULT adapter_gl_create_swapchain(struct wined3d_device *device, struct wined3d_swapchain_desc *desc, struct wined3d_swapchain_state_parent *state_parent, void *parent, const struct wined3d_parent_ops *parent_ops, struct wined3d_swapchain **swapchain) @@ -5057,6 +5079,7 @@ static const struct wined3d_adapter_ops wined3d_adapter_gl_ops = .adapter_unmap_bo_address = adapter_gl_unmap_bo_address, .adapter_copy_bo_address = adapter_gl_copy_bo_address, .adapter_flush_bo_address = adapter_gl_flush_bo_address, + .adapter_destroy_bo = adapter_gl_destroy_bo, .adapter_create_swapchain = adapter_gl_create_swapchain, .adapter_destroy_swapchain = adapter_gl_destroy_swapchain, .adapter_create_buffer = adapter_gl_create_buffer, diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c index 02a359c4f07..9251f790064 100644 --- a/dlls/wined3d/adapter_vk.c +++ b/dlls/wined3d/adapter_vk.c @@ -1182,6 +1182,15 @@ static void adapter_vk_flush_bo_address(struct wined3d_context *context, flush_bo_range(context_vk, bo, (uintptr_t)data->addr, size); }
+static void adapter_vk_destroy_bo(struct wined3d_context *context, struct wined3d_bo *bo) +{ + struct wined3d_bo_vk *bo_vk = wined3d_bo_vk(bo); + + wined3d_context_vk_destroy_bo(wined3d_context_vk(context), bo_vk); + bo_vk->vk_buffer = VK_NULL_HANDLE; + bo_vk->memory = NULL; +} + static HRESULT adapter_vk_create_swapchain(struct wined3d_device *device, struct wined3d_swapchain_desc *desc, struct wined3d_swapchain_state_parent *state_parent, void *parent, const struct wined3d_parent_ops *parent_ops, struct wined3d_swapchain **swapchain) @@ -1834,6 +1843,7 @@ static const struct wined3d_adapter_ops wined3d_adapter_vk_ops = .adapter_unmap_bo_address = adapter_vk_unmap_bo_address, .adapter_copy_bo_address = adapter_vk_copy_bo_address, .adapter_flush_bo_address = adapter_vk_flush_bo_address, + .adapter_destroy_bo = adapter_vk_destroy_bo, .adapter_create_swapchain = adapter_vk_create_swapchain, .adapter_destroy_swapchain = adapter_vk_destroy_swapchain, .adapter_create_buffer = adapter_vk_create_buffer, diff --git a/dlls/wined3d/buffer.c b/dlls/wined3d/buffer.c index 55dcd9e67e8..4aa450bcc28 100644 --- a/dlls/wined3d/buffer.c +++ b/dlls/wined3d/buffer.c @@ -164,35 +164,6 @@ static GLenum wined3d_buffer_gl_binding_from_bind_flags(const struct wined3d_gl_ return GL_ARRAY_BUFFER; }
-/* Context activation is done by the caller. */ -static void wined3d_buffer_gl_destroy_buffer_object(struct wined3d_buffer_gl *buffer_gl, - struct wined3d_context_gl *context_gl) -{ - struct wined3d_resource *resource = &buffer_gl->b.resource; - - if (!buffer_gl->b.buffer_object) - return; - - if (context_gl->c.transform_feedback_active && (resource->bind_flags & WINED3D_BIND_STREAM_OUTPUT) - && wined3d_context_is_graphics_state_dirty(&context_gl->c, STATE_STREAM_OUTPUT)) - { - /* It's illegal to (un)bind GL_TRANSFORM_FEEDBACK_BUFFER while transform - * feedback is active. Deleting a buffer implicitly unbinds it, so we - * need to end transform feedback here if this buffer was bound. - * - * This should only be possible if STATE_STREAM_OUTPUT is dirty; if we - * do a draw call before destroying this buffer then the draw call will - * already rebind the GL target. */ - WARN("Deleting buffer object for buffer %p, disabling transform feedback.\n", buffer_gl); - wined3d_context_gl_end_transform_feedback(context_gl); - } - - buffer_gl->b.bo_user.valid = false; - list_remove(&buffer_gl->b.bo_user.entry); - wined3d_context_gl_destroy_bo(context_gl, &buffer_gl->bo); - buffer_gl->b.buffer_object = 0; -} - /* Context activation is done by the caller. */ static BOOL wined3d_buffer_gl_create_buffer_object(struct wined3d_buffer_gl *buffer_gl, struct wined3d_context_gl *context_gl) @@ -557,12 +528,6 @@ BOOL wined3d_buffer_prepare_location(struct wined3d_buffer *buffer, return buffer->buffer_ops->buffer_prepare_location(buffer, context, location); }
-static void wined3d_buffer_unload_location(struct wined3d_buffer *buffer, - struct wined3d_context *context, unsigned int location) -{ - buffer->buffer_ops->buffer_unload_location(buffer, context, location); -} - BOOL wined3d_buffer_load_location(struct wined3d_buffer *buffer, struct wined3d_context *context, DWORD location) { @@ -674,6 +639,14 @@ DWORD wined3d_buffer_get_memory(struct wined3d_buffer *buffer, struct wined3d_co return 0; }
+static void wined3d_buffer_unload_bo(struct wined3d_buffer *buffer, struct wined3d_context *context) +{ + buffer->bo_user.valid = false; + list_remove(&buffer->bo_user.entry); + context->device->adapter->adapter_ops->adapter_destroy_bo(context, (struct wined3d_bo *)buffer->buffer_object); + buffer->buffer_object = 0u; +} + static void buffer_resource_unload(struct wined3d_resource *resource) { struct wined3d_buffer *buffer = buffer_from_resource(resource); @@ -688,7 +661,7 @@ static void buffer_resource_unload(struct wined3d_resource *resource)
wined3d_buffer_load_location(buffer, context, WINED3D_LOCATION_SYSMEM); wined3d_buffer_invalidate_location(buffer, WINED3D_LOCATION_BUFFER); - wined3d_buffer_unload_location(buffer, context, WINED3D_LOCATION_BUFFER); + wined3d_buffer_unload_bo(buffer, context); buffer_clear_dirty_areas(buffer);
context_release(context); @@ -719,7 +692,7 @@ static void wined3d_buffer_destroy_object(void *object) if (buffer->buffer_object) { context = context_acquire(buffer->resource.device, NULL, 0); - wined3d_buffer_unload_location(buffer, context, WINED3D_LOCATION_BUFFER); + wined3d_buffer_unload_bo(buffer, context); context_release(context); } heap_free(buffer->conversion_map); @@ -1238,12 +1211,6 @@ static BOOL wined3d_buffer_no3d_prepare_location(struct wined3d_buffer *buffer, return FALSE; }
-static void wined3d_buffer_no3d_unload_location(struct wined3d_buffer *buffer, - struct wined3d_context *context, unsigned int location) -{ - TRACE("buffer %p, context %p, location %s.\n", buffer, context, wined3d_debug_location(location)); -} - static void wined3d_buffer_no3d_upload_ranges(struct wined3d_buffer *buffer, struct wined3d_context *context, const void *data, unsigned int data_offset, unsigned int range_count, const struct wined3d_range *ranges) { @@ -1259,7 +1226,6 @@ static void wined3d_buffer_no3d_download_ranges(struct wined3d_buffer *buffer, s static const struct wined3d_buffer_ops wined3d_buffer_no3d_ops = { wined3d_buffer_no3d_prepare_location, - wined3d_buffer_no3d_unload_location, wined3d_buffer_no3d_upload_ranges, wined3d_buffer_no3d_download_ranges, }; @@ -1302,23 +1268,6 @@ static BOOL wined3d_buffer_gl_prepare_location(struct wined3d_buffer *buffer, } }
-static void wined3d_buffer_gl_unload_location(struct wined3d_buffer *buffer, - struct wined3d_context *context, unsigned int location) -{ - TRACE("buffer %p, context %p, location %s.\n", buffer, context, wined3d_debug_location(location)); - - switch (location) - { - case WINED3D_LOCATION_BUFFER: - wined3d_buffer_gl_destroy_buffer_object(wined3d_buffer_gl(buffer), wined3d_context_gl(context)); - break; - - default: - ERR("Unhandled location %s.\n", wined3d_debug_location(location)); - break; - } -} - /* Context activation is done by the caller. */ static void wined3d_buffer_gl_upload_ranges(struct wined3d_buffer *buffer, struct wined3d_context *context, const void *data, unsigned int data_offset, unsigned int range_count, const struct wined3d_range *ranges) @@ -1369,7 +1318,6 @@ static void wined3d_buffer_gl_download_ranges(struct wined3d_buffer *buffer, str static const struct wined3d_buffer_ops wined3d_buffer_gl_ops = { wined3d_buffer_gl_prepare_location, - wined3d_buffer_gl_unload_location, wined3d_buffer_gl_upload_ranges, wined3d_buffer_gl_download_ranges, }; @@ -1480,31 +1428,6 @@ static BOOL wined3d_buffer_vk_prepare_location(struct wined3d_buffer *buffer, } }
-static void wined3d_buffer_vk_unload_location(struct wined3d_buffer *buffer, - struct wined3d_context *context, unsigned int location) -{ - struct wined3d_context_vk *context_vk = wined3d_context_vk(context); - struct wined3d_buffer_vk *buffer_vk = wined3d_buffer_vk(buffer); - - TRACE("buffer %p, context %p, location %s.\n", buffer, context, wined3d_debug_location(location)); - - switch (location) - { - case WINED3D_LOCATION_BUFFER: - buffer_vk->b.bo_user.valid = false; - list_remove(&buffer_vk->b.bo_user.entry); - wined3d_context_vk_destroy_bo(context_vk, &buffer_vk->bo); - buffer_vk->bo.vk_buffer = VK_NULL_HANDLE; - buffer_vk->bo.memory = NULL; - buffer_vk->b.buffer_object = 0u; - break; - - default: - ERR("Unhandled location %s.\n", wined3d_debug_location(location)); - break; - } -} - static void wined3d_buffer_vk_upload_ranges(struct wined3d_buffer *buffer, struct wined3d_context *context, const void *data, unsigned int data_offset, unsigned int range_count, const struct wined3d_range *ranges) { @@ -1568,7 +1491,6 @@ static void wined3d_buffer_vk_download_ranges(struct wined3d_buffer *buffer, str static const struct wined3d_buffer_ops wined3d_buffer_vk_ops = { wined3d_buffer_vk_prepare_location, - wined3d_buffer_vk_unload_location, wined3d_buffer_vk_upload_ranges, wined3d_buffer_vk_download_ranges, }; diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index c265bdc8c95..8a5b61dcd68 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -2805,6 +2805,10 @@ static void adapter_no3d_flush_bo_address(struct wined3d_context *context, { }
+static void adapter_no3d_destroy_bo(struct wined3d_context *context, struct wined3d_bo *bo) +{ +} + static HRESULT adapter_no3d_create_swapchain(struct wined3d_device *device, struct wined3d_swapchain_desc *desc, struct wined3d_swapchain_state_parent *state_parent, void *parent, const struct wined3d_parent_ops *parent_ops, struct wined3d_swapchain **swapchain) @@ -3075,6 +3079,7 @@ static const struct wined3d_adapter_ops wined3d_adapter_no3d_ops = .adapter_unmap_bo_address = adapter_no3d_unmap_bo_address, .adapter_copy_bo_address = adapter_no3d_copy_bo_address, .adapter_flush_bo_address = adapter_no3d_flush_bo_address, + .adapter_destroy_bo = adapter_no3d_destroy_bo, .adapter_create_swapchain = adapter_no3d_create_swapchain, .adapter_destroy_swapchain = adapter_no3d_destroy_swapchain, .adapter_create_buffer = adapter_no3d_create_buffer, diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index 8666d9699c9..246fd1d60ea 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -1609,6 +1609,11 @@ struct wined3d_bo_gl uint64_t command_fence_id; };
+static inline struct wined3d_bo_gl *wined3d_bo_gl(struct wined3d_bo *bo) +{ + return CONTAINING_RECORD(bo, struct wined3d_bo_gl, b); +} + static inline GLuint wined3d_bo_gl_id(uintptr_t bo) { return bo ? ((struct wined3d_bo_gl *)bo)->id : 0; @@ -1639,6 +1644,11 @@ struct wined3d_bo_vk bool host_synced; };
+static inline struct wined3d_bo_vk *wined3d_bo_vk(struct wined3d_bo *bo) +{ + return CONTAINING_RECORD(bo, struct wined3d_bo_vk, b); +} + struct wined3d_bo_slab_vk_key { VkMemoryPropertyFlags memory_type; @@ -3370,6 +3380,7 @@ struct wined3d_adapter_ops const struct wined3d_bo_address *dst, const struct wined3d_bo_address *src, size_t size); void (*adapter_flush_bo_address)(struct wined3d_context *context, const struct wined3d_const_bo_address *data, size_t size); + void (*adapter_destroy_bo)(struct wined3d_context *context, struct wined3d_bo *bo); HRESULT (*adapter_create_swapchain)(struct wined3d_device *device, struct wined3d_swapchain_desc *desc, struct wined3d_swapchain_state_parent *state_parent, void *parent, @@ -4982,8 +4993,6 @@ struct wined3d_buffer_ops { BOOL (*buffer_prepare_location)(struct wined3d_buffer *buffer, struct wined3d_context *context, unsigned int location); - void (*buffer_unload_location)(struct wined3d_buffer *buffer, - struct wined3d_context *context, unsigned int location); void (*buffer_upload_ranges)(struct wined3d_buffer *buffer, struct wined3d_context *context, const void *data, unsigned int data_offset, unsigned int range_count, const struct wined3d_range *ranges); void (*buffer_download_ranges)(struct wined3d_buffer *buffer, struct wined3d_context *context, void *data,