v2: Expose wined3d_streaming_buffer_map() and wined3d_streaming_buffer_unmap() for strided data upload.
-- v2: wined3d: Add a lower size bound for the streaming buffer allocation. ddraw: Use the wined3d_streaming_buffer helpers to manage the streaming index buffer. ddraw: Use the wined3d_streaming_buffer helpers to manage the streaming vertex buffer. wined3d: Factor out and expose functions to map/unmap wined3d_streaming_buffer.
From: Anton Baskanov baskanov@gmail.com
--- dlls/wined3d/buffer.c | 31 +++++++++++++++++++++++++------ dlls/wined3d/wined3d.spec | 2 ++ include/wine/wined3d.h | 4 ++++ 3 files changed, 31 insertions(+), 6 deletions(-)
diff --git a/dlls/wined3d/buffer.c b/dlls/wined3d/buffer.c index 1a953f8e218..fca7f2916b7 100644 --- a/dlls/wined3d/buffer.c +++ b/dlls/wined3d/buffer.c @@ -1685,8 +1685,9 @@ static HRESULT wined3d_streaming_buffer_prepare(struct wined3d_device *device, return hr; }
-HRESULT CDECL wined3d_streaming_buffer_upload(struct wined3d_device *device, struct wined3d_streaming_buffer *buffer, - const void *data, unsigned int size, unsigned int stride, unsigned int *ret_pos) +HRESULT CDECL wined3d_streaming_buffer_map(struct wined3d_device *device, + struct wined3d_streaming_buffer *buffer, unsigned int size, unsigned int stride, + unsigned int *ret_pos, void **ret_data) { unsigned int map_flags = WINED3D_MAP_WRITE; struct wined3d_resource *resource; @@ -1695,8 +1696,8 @@ HRESULT CDECL wined3d_streaming_buffer_upload(struct wined3d_device *device, str struct wined3d_box box; HRESULT hr;
- TRACE("device %p, buffer %p, data %p, size %u, stride %u, ret_pos %p.\n", - device, buffer, data, size, stride, ret_pos); + TRACE("device %p, buffer %p, size %u, stride %u, ret_pos %p, ret_data %p.\n", + device, buffer, size, stride, ret_pos, ret_data);
if (FAILED(hr = wined3d_streaming_buffer_prepare(device, buffer, size))) return hr; @@ -1719,10 +1720,28 @@ HRESULT CDECL wined3d_streaming_buffer_upload(struct wined3d_device *device, str wined3d_box_set(&box, pos, 0, pos + size, 1, 0, 1); if (SUCCEEDED(hr = wined3d_resource_map(resource, 0, &map_desc, &box, map_flags))) { - memcpy(map_desc.data, data, size); - wined3d_resource_unmap(resource, 0); *ret_pos = pos; + *ret_data = map_desc.data; buffer->pos = pos + size; } return hr; } + +void CDECL wined3d_streaming_buffer_unmap(struct wined3d_streaming_buffer *buffer) +{ + wined3d_resource_unmap(&buffer->buffer->resource, 0); +} + +HRESULT CDECL wined3d_streaming_buffer_upload(struct wined3d_device *device, struct wined3d_streaming_buffer *buffer, + const void *data, unsigned int size, unsigned int stride, unsigned int *ret_pos) +{ + void *dst_data; + HRESULT hr; + + if (SUCCEEDED(hr = wined3d_streaming_buffer_map(device, buffer, size, stride, ret_pos, &dst_data))) + { + memcpy(dst_data, data, size); + wined3d_streaming_buffer_unmap(buffer); + } + return hr; +} diff --git a/dlls/wined3d/wined3d.spec b/dlls/wined3d/wined3d.spec index e6126faf838..827ac295ddc 100644 --- a/dlls/wined3d/wined3d.spec +++ b/dlls/wined3d/wined3d.spec @@ -260,6 +260,8 @@ @ cdecl wined3d_stateblock_set_vs_consts_f(ptr long long ptr) @ cdecl wined3d_stateblock_set_vs_consts_i(ptr long long ptr)
+@ cdecl wined3d_streaming_buffer_map(ptr ptr long long ptr ptr) +@ cdecl wined3d_streaming_buffer_unmap(ptr) @ cdecl wined3d_streaming_buffer_upload(ptr ptr ptr long long ptr)
@ cdecl wined3d_swapchain_create(ptr ptr ptr ptr ptr ptr) diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index a18dcda45be..8ec397b73a5 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2788,6 +2788,10 @@ HRESULT __cdecl wined3d_stateblock_set_vs_consts_f(struct wined3d_stateblock *st HRESULT __cdecl wined3d_stateblock_set_vs_consts_i(struct wined3d_stateblock *stateblock, unsigned int start_idx, unsigned int count, const struct wined3d_ivec4 *constants);
+HRESULT __cdecl wined3d_streaming_buffer_map(struct wined3d_device *device, + struct wined3d_streaming_buffer *buffer, unsigned int size, unsigned int stride, + unsigned int *ret_pos, void **ret_data); +void __cdecl wined3d_streaming_buffer_unmap(struct wined3d_streaming_buffer *buffer); HRESULT __cdecl wined3d_streaming_buffer_upload(struct wined3d_device *device, struct wined3d_streaming_buffer *buffer, const void *data, unsigned int size, unsigned int stride, unsigned int *pos);
From: Anton Baskanov baskanov@gmail.com
--- dlls/ddraw/ddraw_private.h | 4 +- dlls/ddraw/device.c | 161 +++++++------------------------------ 2 files changed, 28 insertions(+), 137 deletions(-)
diff --git a/dlls/ddraw/ddraw_private.h b/dlls/ddraw/ddraw_private.h index 1edc459ed79..d2b1fc495fc 100644 --- a/dlls/ddraw/ddraw_private.h +++ b/dlls/ddraw/ddraw_private.h @@ -339,9 +339,7 @@ struct d3d_device UINT index_buffer_size; UINT index_buffer_pos;
- struct wined3d_buffer *vertex_buffer; - UINT vertex_buffer_size; - UINT vertex_buffer_pos; + struct wined3d_streaming_buffer vertex_buffer;
/* Viewport management */ struct list viewport_list; diff --git a/dlls/ddraw/device.c b/dlls/ddraw/device.c index 27b650036cf..19ae3b6cf33 100644 --- a/dlls/ddraw/device.c +++ b/dlls/ddraw/device.c @@ -281,8 +281,7 @@ static ULONG WINAPI d3d_device_inner_Release(IUnknown *iface)
if (This->index_buffer) wined3d_buffer_decref(This->index_buffer); - if (This->vertex_buffer) - wined3d_buffer_decref(This->vertex_buffer); + wined3d_streaming_buffer_cleanup(&This->vertex_buffer);
wined3d_device_context_set_rendertarget_views(This->immediate_context, 0, 1, &null_rtv, FALSE);
@@ -3391,44 +3390,6 @@ static HRESULT WINAPI d3d_device2_MultiplyTransform(IDirect3DDevice2 *iface, * DDERR_INVALIDPARAMS if Vertices is NULL * *****************************************************************************/ - -/* The caller is responsible for wined3d locking */ -static HRESULT d3d_device_prepare_vertex_buffer(struct d3d_device *device, UINT min_size) -{ - HRESULT hr; - - if (device->vertex_buffer_size < min_size || !device->vertex_buffer) - { - UINT size = max(device->vertex_buffer_size * 2, min_size); - struct wined3d_buffer_desc desc; - struct wined3d_buffer *buffer; - - TRACE("Growing vertex buffer to %u bytes\n", size); - - desc.byte_width = size; - desc.usage = WINED3DUSAGE_DYNAMIC; - desc.bind_flags = WINED3D_BIND_VERTEX_BUFFER; - desc.access = WINED3D_RESOURCE_ACCESS_GPU | WINED3D_RESOURCE_ACCESS_MAP_W; - desc.misc_flags = 0; - desc.structure_byte_stride = 0; - - if (FAILED(hr = wined3d_buffer_create(device->wined3d_device, &desc, - NULL, NULL, &ddraw_null_wined3d_parent_ops, &buffer))) - { - ERR("Failed to create vertex buffer, hr %#lx.\n", hr); - return hr; - } - - if (device->vertex_buffer) - wined3d_buffer_decref(device->vertex_buffer); - - device->vertex_buffer = buffer; - device->vertex_buffer_size = size; - device->vertex_buffer_pos = 0; - } - return D3D_OK; -} - static void d3d_device_sync_rendertarget(struct d3d_device *device) { struct wined3d_rendertarget_view *rtv; @@ -3475,10 +3436,7 @@ static HRESULT d3d_device7_DrawPrimitive(IDirect3DDevice7 *iface, DWORD vertex_count, DWORD flags) { struct d3d_device *device = impl_from_IDirect3DDevice7(iface); - struct wined3d_map_desc wined3d_map_desc; - struct wined3d_box wined3d_box = {0}; - UINT stride, vb_pos, size, align; - struct wined3d_resource *vb; + UINT stride, vb_pos, size; HRESULT hr;
TRACE("iface %p, primitive_type %#x, fvf %#lx, vertices %p, vertex_count %lu, flags %#lx.\n", @@ -3495,29 +3453,12 @@ static HRESULT d3d_device7_DrawPrimitive(IDirect3DDevice7 *iface, size = vertex_count * stride;
wined3d_mutex_lock(); - hr = d3d_device_prepare_vertex_buffer(device, size); - if (FAILED(hr)) - goto done;
- vb_pos = device->vertex_buffer_pos; - align = vb_pos % stride; - if (align) align = stride - align; - if (vb_pos + size + align > device->vertex_buffer_size) - vb_pos = 0; - else - vb_pos += align; - - wined3d_box.left = vb_pos; - wined3d_box.right = vb_pos + size; - vb = wined3d_buffer_get_resource(device->vertex_buffer); - if (FAILED(hr = wined3d_resource_map(vb, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (vb_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_upload(device->wined3d_device, + &device->vertex_buffer, vertices, size, stride, &vb_pos))) goto done; - memcpy(wined3d_map_desc.data, vertices, size); - wined3d_resource_unmap(vb, 0); - device->vertex_buffer_pos = vb_pos + size;
- hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer, 0, stride); + hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer.buffer, 0, stride); if (FAILED(hr)) goto done;
@@ -3674,8 +3615,8 @@ static HRESULT d3d_device7_DrawIndexedPrimitive(IDirect3DDevice7 *iface, UINT vtx_size = stride * vertex_count, idx_size = index_count * sizeof(*indices); struct wined3d_map_desc wined3d_map_desc; struct wined3d_box wined3d_box = {0}; - struct wined3d_resource *ib, *vb; - UINT vb_pos, ib_pos, align; + struct wined3d_resource *ib; + UINT vb_pos, ib_pos;
TRACE("iface %p, primitive_type %#x, fvf %#lx, vertices %p, vertex_count %lu, " "indices %p, index_count %lu, flags %#lx.\n", @@ -3690,27 +3631,9 @@ static HRESULT d3d_device7_DrawIndexedPrimitive(IDirect3DDevice7 *iface, /* Set the D3DDevice's FVF */ wined3d_mutex_lock();
- hr = d3d_device_prepare_vertex_buffer(device, vtx_size); - if (FAILED(hr)) - goto done; - - vb_pos = device->vertex_buffer_pos; - align = vb_pos % stride; - if (align) align = stride - align; - if (vb_pos + vtx_size + align > device->vertex_buffer_size) - vb_pos = 0; - else - vb_pos += align; - - wined3d_box.left = vb_pos; - wined3d_box.right = vb_pos + vtx_size; - vb = wined3d_buffer_get_resource(device->vertex_buffer); - if (FAILED(hr = wined3d_resource_map(vb, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (vb_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_upload(device->wined3d_device, + &device->vertex_buffer, vertices, vtx_size, stride, &vb_pos))) goto done; - memcpy(wined3d_map_desc.data, vertices, vtx_size); - wined3d_resource_unmap(vb, 0); - device->vertex_buffer_pos = vb_pos + vtx_size;
hr = d3d_device_prepare_index_buffer(device, idx_size); if (FAILED(hr)) @@ -3729,7 +3652,7 @@ static HRESULT d3d_device7_DrawIndexedPrimitive(IDirect3DDevice7 *iface, wined3d_resource_unmap(ib, 0); device->index_buffer_pos = ib_pos + idx_size;
- hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer, 0, stride); + hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer.buffer, 0, stride); if (FAILED(hr)) goto done; wined3d_stateblock_set_index_buffer(device->state, device->index_buffer, WINED3DFMT_R16_UINT); @@ -4022,10 +3945,8 @@ static HRESULT d3d_device7_DrawPrimitiveStrided(IDirect3DDevice7 *iface, D3DPRIM HRESULT hr; UINT dst_stride = get_flexible_vertex_size(fvf); UINT dst_size = dst_stride * vertex_count; - struct wined3d_map_desc wined3d_map_desc; - struct wined3d_box wined3d_box = {0}; - struct wined3d_resource *vb; - UINT vb_pos, align; + void *dst_data; + UINT vb_pos;
TRACE("iface %p, primitive_type %#x, fvf %#lx, strided_data %p, vertex_count %lu, flags %#lx.\n", iface, primitive_type, fvf, strided_data, vertex_count, flags); @@ -4037,29 +3958,14 @@ static HRESULT d3d_device7_DrawPrimitiveStrided(IDirect3DDevice7 *iface, D3DPRIM }
wined3d_mutex_lock(); - hr = d3d_device_prepare_vertex_buffer(device, dst_size); - if (FAILED(hr)) - goto done;
- vb_pos = device->vertex_buffer_pos; - align = vb_pos % dst_stride; - if (align) align = dst_stride - align; - if (vb_pos + dst_size + align > device->vertex_buffer_size) - vb_pos = 0; - else - vb_pos += align; - - wined3d_box.left = vb_pos; - wined3d_box.right = vb_pos + dst_size; - vb = wined3d_buffer_get_resource(device->vertex_buffer); - if (FAILED(hr = wined3d_resource_map(vb, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (vb_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_map(device->wined3d_device, + &device->vertex_buffer, dst_size, dst_stride, &vb_pos, &dst_data))) goto done; - pack_strided_data(wined3d_map_desc.data, vertex_count, strided_data, fvf); - wined3d_resource_unmap(vb, 0); - device->vertex_buffer_pos = vb_pos + dst_size; + pack_strided_data(dst_data, vertex_count, strided_data, fvf); + wined3d_streaming_buffer_unmap(&device->vertex_buffer);
- hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer, 0, dst_stride); + hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer.buffer, 0, dst_stride); if (FAILED(hr)) goto done; wined3d_stateblock_set_vertex_declaration(device->state, ddraw_find_decl(device->ddraw, fvf)); @@ -4139,8 +4045,9 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveStrided(IDirect3DDevice7 *iface, UINT idx_size = index_count * sizeof(WORD); struct wined3d_map_desc wined3d_map_desc; struct wined3d_box wined3d_box = {0}; - struct wined3d_resource *ib, *vb; - UINT vb_pos, align; + struct wined3d_resource *ib; + void *dst_data; + UINT vb_pos; UINT ib_pos; HRESULT hr;
@@ -4156,27 +4063,11 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveStrided(IDirect3DDevice7 *iface,
wined3d_mutex_lock();
- hr = d3d_device_prepare_vertex_buffer(device, vtx_dst_size); - if (FAILED(hr)) - goto done; - - vb_pos = device->vertex_buffer_pos; - align = vb_pos % vtx_dst_stride; - if (align) align = vtx_dst_stride - align; - if (vb_pos + vtx_dst_size + align > device->vertex_buffer_size) - vb_pos = 0; - else - vb_pos += align; - - wined3d_box.left = vb_pos; - wined3d_box.right = vb_pos + vtx_dst_size; - vb = wined3d_buffer_get_resource(device->vertex_buffer); - if (FAILED(hr = wined3d_resource_map(vb, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (vb_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_map(device->wined3d_device, + &device->vertex_buffer, vtx_dst_size, vtx_dst_stride, &vb_pos, &dst_data))) goto done; - pack_strided_data(wined3d_map_desc.data, vertex_count, strided_data, fvf); - wined3d_resource_unmap(vb, 0); - device->vertex_buffer_pos = vb_pos + vtx_dst_size; + pack_strided_data(dst_data, vertex_count, strided_data, fvf); + wined3d_streaming_buffer_unmap(&device->vertex_buffer);
hr = d3d_device_prepare_index_buffer(device, idx_size); if (FAILED(hr)) @@ -4195,7 +4086,7 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveStrided(IDirect3DDevice7 *iface, wined3d_resource_unmap(ib, 0); device->index_buffer_pos = ib_pos + idx_size;
- hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer, 0, vtx_dst_stride); + hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer.buffer, 0, vtx_dst_stride); if (FAILED(hr)) goto done; wined3d_stateblock_set_index_buffer(device->state, device->index_buffer, WINED3DFMT_R16_UINT); @@ -7052,6 +6943,8 @@ static HRESULT d3d_device_init(struct d3d_device *device, struct ddraw *ddraw, c device->stateblock_state = ddraw->stateblock_state; wined3d_stateblock_incref(ddraw->state);
+ wined3d_streaming_buffer_init(&device->vertex_buffer, WINED3D_BIND_VERTEX_BUFFER); + /* Render to the back buffer */ rtv = ddraw_surface_get_rendertarget_view(target); if (FAILED(hr = wined3d_device_context_set_rendertarget_views(device->immediate_context, 0, 1, &rtv, TRUE)))
From: Anton Baskanov baskanov@gmail.com
--- dlls/ddraw/ddraw_private.h | 6 +- dlls/ddraw/device.c | 110 ++++--------------------------------- 2 files changed, 12 insertions(+), 104 deletions(-)
diff --git a/dlls/ddraw/ddraw_private.h b/dlls/ddraw/ddraw_private.h index d2b1fc495fc..6693a650394 100644 --- a/dlls/ddraw/ddraw_private.h +++ b/dlls/ddraw/ddraw_private.h @@ -335,11 +335,7 @@ struct d3d_device struct ddraw *ddraw; IUnknown *rt_iface;
- struct wined3d_buffer *index_buffer; - UINT index_buffer_size; - UINT index_buffer_pos; - - struct wined3d_streaming_buffer vertex_buffer; + struct wined3d_streaming_buffer vertex_buffer, index_buffer;
/* Viewport management */ struct list viewport_list; diff --git a/dlls/ddraw/device.c b/dlls/ddraw/device.c index 19ae3b6cf33..ac6647b8dad 100644 --- a/dlls/ddraw/device.c +++ b/dlls/ddraw/device.c @@ -279,8 +279,7 @@ static ULONG WINAPI d3d_device_inner_Release(IUnknown *iface) /* There is no need to unset any resources here, wined3d will take * care of that on uninit_3d(). */
- if (This->index_buffer) - wined3d_buffer_decref(This->index_buffer); + wined3d_streaming_buffer_cleanup(&This->index_buffer); wined3d_streaming_buffer_cleanup(&This->vertex_buffer);
wined3d_device_context_set_rendertarget_views(This->immediate_context, 0, 1, &null_rtv, FALSE); @@ -3569,42 +3568,6 @@ static HRESULT WINAPI d3d_device2_DrawPrimitive(IDirect3DDevice2 *iface, * DDERR_INVALIDPARAMS if Vertices or Indices is NULL * *****************************************************************************/ -/* The caller is responsible for wined3d locking */ -static HRESULT d3d_device_prepare_index_buffer(struct d3d_device *device, UINT min_size) -{ - HRESULT hr; - - if (device->index_buffer_size < min_size || !device->index_buffer) - { - UINT size = max(device->index_buffer_size * 2, min_size); - struct wined3d_buffer_desc desc; - struct wined3d_buffer *buffer; - - TRACE("Growing index buffer to %u bytes\n", size); - - desc.byte_width = size; - desc.usage = WINED3DUSAGE_DYNAMIC | WINED3DUSAGE_STATICDECL; - desc.bind_flags = WINED3D_BIND_INDEX_BUFFER; - desc.access = WINED3D_RESOURCE_ACCESS_GPU | WINED3D_RESOURCE_ACCESS_MAP_W; - desc.misc_flags = 0; - desc.structure_byte_stride = 0; - - if (FAILED(hr = wined3d_buffer_create(device->wined3d_device, &desc, - NULL, NULL, &ddraw_null_wined3d_parent_ops, &buffer))) - { - ERR("Failed to create index buffer, hr %#lx.\n", hr); - return hr; - } - - if (device->index_buffer) - wined3d_buffer_decref(device->index_buffer); - device->index_buffer = buffer; - device->index_buffer_size = size; - device->index_buffer_pos = 0; - } - return D3D_OK; -} - static HRESULT d3d_device7_DrawIndexedPrimitive(IDirect3DDevice7 *iface, D3DPRIMITIVETYPE primitive_type, DWORD fvf, void *vertices, DWORD vertex_count, WORD *indices, DWORD index_count, DWORD flags) @@ -3613,9 +3576,6 @@ static HRESULT d3d_device7_DrawIndexedPrimitive(IDirect3DDevice7 *iface, HRESULT hr; UINT stride = get_flexible_vertex_size(fvf); UINT vtx_size = stride * vertex_count, idx_size = index_count * sizeof(*indices); - struct wined3d_map_desc wined3d_map_desc; - struct wined3d_box wined3d_box = {0}; - struct wined3d_resource *ib; UINT vb_pos, ib_pos;
TRACE("iface %p, primitive_type %#x, fvf %#lx, vertices %p, vertex_count %lu, " @@ -3635,27 +3595,14 @@ static HRESULT d3d_device7_DrawIndexedPrimitive(IDirect3DDevice7 *iface, &device->vertex_buffer, vertices, vtx_size, stride, &vb_pos))) goto done;
- hr = d3d_device_prepare_index_buffer(device, idx_size); - if (FAILED(hr)) - goto done; - ib_pos = device->index_buffer_pos; - if (device->index_buffer_size - idx_size < ib_pos) - ib_pos = 0; - - wined3d_box.left = ib_pos; - wined3d_box.right = ib_pos + idx_size; - ib = wined3d_buffer_get_resource(device->index_buffer); - if (FAILED(hr = wined3d_resource_map(ib, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (ib_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_upload(device->wined3d_device, + &device->index_buffer, indices, idx_size, sizeof(*indices), &ib_pos))) goto done; - memcpy(wined3d_map_desc.data, indices, idx_size); - wined3d_resource_unmap(ib, 0); - device->index_buffer_pos = ib_pos + idx_size;
hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer.buffer, 0, stride); if (FAILED(hr)) goto done; - wined3d_stateblock_set_index_buffer(device->state, device->index_buffer, WINED3DFMT_R16_UINT); + wined3d_stateblock_set_index_buffer(device->state, device->index_buffer.buffer, WINED3DFMT_R16_UINT);
wined3d_stateblock_set_vertex_declaration(device->state, ddraw_find_decl(device->ddraw, fvf)); wined3d_device_context_set_primitive_type(device->immediate_context, @@ -4043,9 +3990,6 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveStrided(IDirect3DDevice7 *iface, UINT vtx_dst_stride = get_flexible_vertex_size(fvf); UINT vtx_dst_size = vertex_count * vtx_dst_stride; UINT idx_size = index_count * sizeof(WORD); - struct wined3d_map_desc wined3d_map_desc; - struct wined3d_box wined3d_box = {0}; - struct wined3d_resource *ib; void *dst_data; UINT vb_pos; UINT ib_pos; @@ -4069,27 +4013,14 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveStrided(IDirect3DDevice7 *iface, pack_strided_data(dst_data, vertex_count, strided_data, fvf); wined3d_streaming_buffer_unmap(&device->vertex_buffer);
- hr = d3d_device_prepare_index_buffer(device, idx_size); - if (FAILED(hr)) - goto done; - ib_pos = device->index_buffer_pos; - if (device->index_buffer_size - idx_size < ib_pos) - ib_pos = 0; - - wined3d_box.left = ib_pos; - wined3d_box.right = ib_pos + idx_size; - ib = wined3d_buffer_get_resource(device->index_buffer); - if (FAILED(hr = wined3d_resource_map(ib, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (ib_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_upload(device->wined3d_device, + &device->index_buffer, indices, idx_size, sizeof(WORD), &ib_pos))) goto done; - memcpy(wined3d_map_desc.data, indices, idx_size); - wined3d_resource_unmap(ib, 0); - device->index_buffer_pos = ib_pos + idx_size;
hr = wined3d_stateblock_set_stream_source(device->state, 0, device->vertex_buffer.buffer, 0, vtx_dst_stride); if (FAILED(hr)) goto done; - wined3d_stateblock_set_index_buffer(device->state, device->index_buffer, WINED3DFMT_R16_UINT); + wined3d_stateblock_set_index_buffer(device->state, device->index_buffer.buffer, WINED3DFMT_R16_UINT);
wined3d_stateblock_set_vertex_declaration(device->state, ddraw_find_decl(device->ddraw, fvf)); wined3d_device_context_set_primitive_type(device->immediate_context, @@ -4291,7 +4222,6 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveVB(IDirect3DDevice7 *iface, struct wined3d_resource *wined3d_resource; struct wined3d_map_desc wined3d_map_desc; struct wined3d_box wined3d_box = {0}; - struct wined3d_resource *ib; HRESULT hr; UINT ib_pos;
@@ -4338,34 +4268,15 @@ static HRESULT d3d_device7_DrawIndexedPrimitiveVB(IDirect3DDevice7 *iface,
wined3d_stateblock_set_vertex_declaration(device->state, vb_impl->wined3d_declaration);
- hr = d3d_device_prepare_index_buffer(device, index_count * sizeof(WORD)); - if (FAILED(hr)) - { - wined3d_mutex_unlock(); - return hr; - } - ib_pos = device->index_buffer_pos; - - if (device->index_buffer_size - index_count * sizeof(WORD) < ib_pos) - ib_pos = 0; - - /* Copy the index stream into the index buffer. */ - wined3d_box.left = ib_pos; - wined3d_box.right = ib_pos + index_count * sizeof(WORD); - ib = wined3d_buffer_get_resource(device->index_buffer); - if (FAILED(hr = wined3d_resource_map(ib, 0, &wined3d_map_desc, &wined3d_box, - WINED3D_MAP_WRITE | (ib_pos ? WINED3D_MAP_NOOVERWRITE : WINED3D_MAP_DISCARD)))) + if (FAILED(hr = wined3d_streaming_buffer_upload(device->wined3d_device, + &device->index_buffer, indices, index_count * sizeof(WORD), sizeof(WORD), &ib_pos))) { - ERR("Failed to map buffer, hr %#lx.\n", hr); wined3d_mutex_unlock(); return hr; } - memcpy(wined3d_map_desc.data, indices, index_count * sizeof(WORD)); - wined3d_resource_unmap(ib, 0); - device->index_buffer_pos = ib_pos + index_count * sizeof(WORD);
/* Set the index stream */ - wined3d_stateblock_set_index_buffer(device->state, device->index_buffer, WINED3DFMT_R16_UINT); + wined3d_stateblock_set_index_buffer(device->state, device->index_buffer.buffer, WINED3DFMT_R16_UINT);
/* Set the vertex stream source */ if (FAILED(hr = wined3d_stateblock_set_stream_source(device->state, @@ -6944,6 +6855,7 @@ static HRESULT d3d_device_init(struct d3d_device *device, struct ddraw *ddraw, c wined3d_stateblock_incref(ddraw->state);
wined3d_streaming_buffer_init(&device->vertex_buffer, WINED3D_BIND_VERTEX_BUFFER); + wined3d_streaming_buffer_init(&device->index_buffer, WINED3D_BIND_INDEX_BUFFER);
/* Render to the back buffer */ rtv = ddraw_surface_get_rendertarget_view(target);
From: Anton Baskanov baskanov@gmail.com
Apps that issues many small draw calls (e.g. Earth 2150) may cause frequent DISCARD maps, which are significantly slower than NOOVERWRITE ones. --- dlls/wined3d/buffer.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/dlls/wined3d/buffer.c b/dlls/wined3d/buffer.c index fca7f2916b7..74c2a1b8b2b 100644 --- a/dlls/wined3d/buffer.c +++ b/dlls/wined3d/buffer.c @@ -34,6 +34,8 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d); #define VB_MAXFULLCONVERSIONS 5 /* Number of full conversions before we stop converting */ #define VB_RESETFULLCONVS 20 /* Reset full conversion counts after that number of draws */
+#define SB_MIN_SIZE (512 * 1024) /* Minimum size of an allocated streaming buffer. */ + struct wined3d_buffer_ops { BOOL (*buffer_prepare_location)(struct wined3d_buffer *buffer, @@ -1665,7 +1667,7 @@ static HRESULT wined3d_streaming_buffer_prepare(struct wined3d_device *device, return S_OK; }
- size = max(old_size * 2, min_size); + size = max(SB_MIN_SIZE, max(old_size * 2, min_size)); TRACE("Growing buffer to %u bytes.\n", size);
desc.byte_width = size;
Hi,
It looks like your patch introduced the new failures shown below. Please investigate and fix them before resubmitting your patch. If they are not new, fixing them anyway would help a lot. Otherwise please ask for the known failures list to be updated.
The tests also ran into some preexisting test failures. If you know how to fix them that would be helpful. See the TestBot job for the details:
The full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=126612
Your paranoid android.
=== debian11 (32 bit report) ===
d3d8: stateblock: Timeout visual: Timeout
d3d9: d3d9ex: Timeout device: Timeout stateblock: Timeout visual: Timeout
d3dcompiler_43: asm: Timeout blob: Timeout hlsl_d3d11: Timeout hlsl_d3d9: Timeout reflection: Timeout
d3dcompiler_46: asm: Timeout blob: Timeout hlsl_d3d11: Timeout hlsl_d3d9: Timeout reflection: Timeout
d3dcompiler_47: asm: Timeout blob: Timeout hlsl_d3d11: Timeout hlsl_d3d9: Timeout reflection: Timeout
d3drm: d3drm: Timeout vector: Timeout
d3dx10_34: d3dx10: Timeout
d3dx10_35: d3dx10: Timeout
d3dx10_36: d3dx10: Timeout
d3dx10_37: d3dx10: Timeout
d3dx10_38: d3dx10: Timeout
d3dx10_39: d3dx10: Timeout
d3dx10_40: d3dx10: Timeout
d3dx10_41: d3dx10: Timeout
d3dx10_42: d3dx10: Timeout
d3dx10_43: d3dx10: Timeout
d3dx11_42: d3dx11: Timeout
Report validation errors: d3dx11_43:d3dx11 timeout
=== debian11 (build log) ===
WineRunWineTest.pl:error: The task timed out
On Tue Nov 22 08:43:53 2022 +0000, Henri Verbeet wrote:
I had a cursory look at this, and broadly it seems fine. I don't like the introduction of wined3d_draw_primitive_strided_data though, and think it could easily be avoided by exposing wined3d_streaming_buffer_map()/wined3d_streaming_buffer_unmap() instead.
Done in v2.
Certainly not a line by line review, but conceptually this looks good to me.
This merge request was approved by Jan Sikorski.