Signed-off-by: Zebediah Figura z.figura12@gmail.com --- dlls/d3d11/device.c | 35 +++++++++++------------- dlls/wined3d/cs.c | 49 ++++++++++++++++------------------ dlls/wined3d/device.c | 40 +++++++++++---------------- dlls/wined3d/wined3d.spec | 2 +- dlls/wined3d/wined3d_private.h | 10 ++----- include/wine/wined3d.h | 10 +++++-- 6 files changed, 65 insertions(+), 81 deletions(-)
diff --git a/dlls/d3d11/device.c b/dlls/d3d11/device.c index 578e572797a..79cc7e8c8da 100644 --- a/dlls/d3d11/device.c +++ b/dlls/d3d11/device.c @@ -1172,24 +1172,22 @@ static void STDMETHODCALLTYPE d3d11_device_context_OMSetDepthStencilState(ID3D11 static void STDMETHODCALLTYPE d3d11_device_context_SOSetTargets(ID3D11DeviceContext1 *iface, UINT buffer_count, ID3D11Buffer *const *buffers, const UINT *offsets) { + struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS] = {0}; struct d3d11_device_context *context = impl_from_ID3D11DeviceContext1(iface); - unsigned int count, i; + unsigned int i;
TRACE("iface %p, buffer_count %u, buffers %p, offsets %p.\n", iface, buffer_count, buffers, offsets);
- count = min(buffer_count, D3D11_SO_BUFFER_SLOT_COUNT); - wined3d_mutex_lock(); - for (i = 0; i < count; ++i) + for (i = 0; i < buffer_count; ++i) { struct d3d_buffer *buffer = unsafe_impl_from_ID3D11Buffer(buffers[i]);
- wined3d_device_context_set_stream_output(context->wined3d_context, i, - buffer ? buffer->wined3d_buffer : NULL, offsets ? offsets[i] : 0); - } - for (; i < D3D11_SO_BUFFER_SLOT_COUNT; ++i) - { - wined3d_device_context_set_stream_output(context->wined3d_context, i, NULL, 0); + outputs[i].buffer = buffer ? buffer->wined3d_buffer : NULL; + outputs[i].offset = offsets ? offsets[i] : 0; } + + wined3d_mutex_lock(); + wined3d_device_context_set_stream_outputs(context->wined3d_context, outputs); wined3d_mutex_unlock(); }
@@ -4895,25 +4893,22 @@ static void STDMETHODCALLTYPE d3d10_device_OMSetDepthStencilState(ID3D10Device1 static void STDMETHODCALLTYPE d3d10_device_SOSetTargets(ID3D10Device1 *iface, UINT target_count, ID3D10Buffer *const *targets, const UINT *offsets) { + struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS] = {0}; struct d3d_device *device = impl_from_ID3D10Device(iface); - unsigned int count, i; + unsigned int i;
TRACE("iface %p, target_count %u, targets %p, offsets %p.\n", iface, target_count, targets, offsets);
- count = min(target_count, D3D10_SO_BUFFER_SLOT_COUNT); - wined3d_mutex_lock(); - for (i = 0; i < count; ++i) + for (i = 0; i < target_count; ++i) { struct d3d_buffer *buffer = unsafe_impl_from_ID3D10Buffer(targets[i]);
- wined3d_device_context_set_stream_output(device->immediate_context.wined3d_context, i, - buffer ? buffer->wined3d_buffer : NULL, offsets[i]); + outputs[i].buffer = buffer ? buffer->wined3d_buffer : NULL; + outputs[i].offset = offsets ? offsets[i] : 0; }
- for (i = count; i < D3D10_SO_BUFFER_SLOT_COUNT; ++i) - { - wined3d_device_context_set_stream_output(device->immediate_context.wined3d_context, i, NULL, 0); - } + wined3d_mutex_lock(); + wined3d_device_context_set_stream_outputs(device->immediate_context.wined3d_context, outputs); wined3d_mutex_unlock(); }
diff --git a/dlls/wined3d/cs.c b/dlls/wined3d/cs.c index c3702ab1527..0f950f23f0f 100644 --- a/dlls/wined3d/cs.c +++ b/dlls/wined3d/cs.c @@ -114,7 +114,7 @@ enum wined3d_cs_op WINED3D_CS_OP_SET_VERTEX_DECLARATION, WINED3D_CS_OP_SET_STREAM_SOURCE, WINED3D_CS_OP_SET_STREAM_SOURCE_FREQ, - WINED3D_CS_OP_SET_STREAM_OUTPUT, + WINED3D_CS_OP_SET_STREAM_OUTPUTS, WINED3D_CS_OP_SET_INDEX_BUFFER, WINED3D_CS_OP_SET_CONSTANT_BUFFERS, WINED3D_CS_OP_SET_TEXTURE, @@ -266,12 +266,10 @@ struct wined3d_cs_set_stream_source_freq UINT flags; };
-struct wined3d_cs_set_stream_output +struct wined3d_cs_set_stream_outputs { enum wined3d_cs_op opcode; - UINT stream_idx; - struct wined3d_buffer *buffer; - UINT offset; + struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS]; };
struct wined3d_cs_set_index_buffer @@ -608,7 +606,7 @@ static const char *debug_cs_op(enum wined3d_cs_op op) WINED3D_TO_STR(WINED3D_CS_OP_SET_VERTEX_DECLARATION); WINED3D_TO_STR(WINED3D_CS_OP_SET_STREAM_SOURCE); WINED3D_TO_STR(WINED3D_CS_OP_SET_STREAM_SOURCE_FREQ); - WINED3D_TO_STR(WINED3D_CS_OP_SET_STREAM_OUTPUT); + WINED3D_TO_STR(WINED3D_CS_OP_SET_STREAM_OUTPUTS); WINED3D_TO_STR(WINED3D_CS_OP_SET_INDEX_BUFFER); WINED3D_TO_STR(WINED3D_CS_OP_SET_CONSTANT_BUFFERS); WINED3D_TO_STR(WINED3D_CS_OP_SET_TEXTURE); @@ -1477,35 +1475,34 @@ void wined3d_cs_emit_set_stream_source_freq(struct wined3d_cs *cs, UINT stream_i wined3d_device_context_submit(&cs->c, WINED3D_CS_QUEUE_DEFAULT); }
-static void wined3d_cs_exec_set_stream_output(struct wined3d_cs *cs, const void *data) +static void wined3d_cs_exec_set_stream_outputs(struct wined3d_cs *cs, const void *data) { - const struct wined3d_cs_set_stream_output *op = data; - struct wined3d_stream_output *stream; - struct wined3d_buffer *prev; + const struct wined3d_cs_set_stream_outputs *op = data; + unsigned int i;
- stream = &cs->state.stream_output[op->stream_idx]; - prev = stream->buffer; - stream->buffer = op->buffer; - stream->offset = op->offset; + for (i = 0; i < WINED3D_MAX_STREAM_OUTPUT_BUFFERS; ++i) + { + struct wined3d_buffer *prev = cs->state.stream_output[i].buffer; + struct wined3d_buffer *buffer = op->outputs[i].buffer;
- if (op->buffer) - InterlockedIncrement(&op->buffer->resource.bind_count); - if (prev) - InterlockedDecrement(&prev->resource.bind_count); + if (buffer) + InterlockedIncrement(&buffer->resource.bind_count); + if (prev) + InterlockedDecrement(&prev->resource.bind_count); + }
+ memcpy(cs->state.stream_output, op->outputs, sizeof(op->outputs)); device_invalidate_state(cs->c.device, STATE_STREAM_OUTPUT); }
-void wined3d_device_context_emit_set_stream_output(struct wined3d_device_context *context, unsigned int stream_idx, - struct wined3d_buffer *buffer, unsigned int offset) +void wined3d_device_context_emit_set_stream_outputs(struct wined3d_device_context *context, + const struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS]) { - struct wined3d_cs_set_stream_output *op; + struct wined3d_cs_set_stream_outputs *op;
op = wined3d_device_context_require_space(context, sizeof(*op), WINED3D_CS_QUEUE_DEFAULT); - op->opcode = WINED3D_CS_OP_SET_STREAM_OUTPUT; - op->stream_idx = stream_idx; - op->buffer = buffer; - op->offset = offset; + op->opcode = WINED3D_CS_OP_SET_STREAM_OUTPUTS; + memcpy(op->outputs, outputs, sizeof(op->outputs));
wined3d_device_context_submit(context, WINED3D_CS_QUEUE_DEFAULT); } @@ -2949,7 +2946,7 @@ static void (* const wined3d_cs_op_handlers[])(struct wined3d_cs *cs, const void /* WINED3D_CS_OP_SET_VERTEX_DECLARATION */ wined3d_cs_exec_set_vertex_declaration, /* WINED3D_CS_OP_SET_STREAM_SOURCE */ wined3d_cs_exec_set_stream_source, /* WINED3D_CS_OP_SET_STREAM_SOURCE_FREQ */ wined3d_cs_exec_set_stream_source_freq, - /* WINED3D_CS_OP_SET_STREAM_OUTPUT */ wined3d_cs_exec_set_stream_output, + /* WINED3D_CS_OP_SET_STREAM_OUTPUTS */ wined3d_cs_exec_set_stream_outputs, /* WINED3D_CS_OP_SET_INDEX_BUFFER */ wined3d_cs_exec_set_index_buffer, /* WINED3D_CS_OP_SET_CONSTANT_BUFFERS */ wined3d_cs_exec_set_constant_buffers, /* WINED3D_CS_OP_SET_TEXTURE */ wined3d_cs_exec_set_texture, diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index faf11d25dcb..b846875d865 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -1676,11 +1676,7 @@ void CDECL wined3d_device_context_set_state(struct wined3d_device_context *conte wined3d_device_context_emit_set_depth_stencil_view(context, state->fb.depth_stencil); wined3d_device_context_emit_set_vertex_declaration(context, state->vertex_declaration);
- for (i = 0; i < WINED3D_MAX_STREAM_OUTPUT_BUFFERS; ++i) - { - wined3d_device_context_emit_set_stream_output(context, i, - state->stream_output[i].buffer, state->stream_output[i].offset); - } + wined3d_device_context_emit_set_stream_outputs(context, state->stream_output);
for (i = 0; i < WINED3D_MAX_STREAMS; ++i) { @@ -2332,30 +2328,26 @@ void CDECL wined3d_device_context_set_vertex_declaration(struct wined3d_device_c wined3d_vertex_declaration_decref(prev); }
-void CDECL wined3d_device_context_set_stream_output(struct wined3d_device_context *context, unsigned int idx, - struct wined3d_buffer *buffer, unsigned int offset) +void CDECL wined3d_device_context_set_stream_outputs(struct wined3d_device_context *context, + const struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS]) { - struct wined3d_stream_output *stream; - struct wined3d_buffer *prev_buffer; + struct wined3d_state *state = context->state; + unsigned int i;
- TRACE("context %p, idx %u, buffer %p, offset %u.\n", context, idx, buffer, offset); + TRACE("context %p, outputs %p.\n", context, outputs);
- if (idx >= WINED3D_MAX_STREAM_OUTPUT_BUFFERS) + wined3d_device_context_emit_set_stream_outputs(context, outputs); + for (i = 0; i < WINED3D_MAX_STREAM_OUTPUT_BUFFERS; ++i) { - WARN("Invalid stream output %u.\n", idx); - return; + struct wined3d_buffer *prev_buffer = state->stream_output[i].buffer; + struct wined3d_buffer *buffer = outputs[i].buffer; + + if (buffer) + wined3d_buffer_incref(buffer); + state->stream_output[i] = outputs[i]; + if (prev_buffer) + wined3d_buffer_decref(prev_buffer); } - - stream = &context->state->stream_output[idx]; - prev_buffer = stream->buffer; - - if (buffer) - wined3d_buffer_incref(buffer); - stream->buffer = buffer; - stream->offset = offset; - wined3d_device_context_emit_set_stream_output(context, idx, buffer, offset); - if (prev_buffer) - wined3d_buffer_decref(prev_buffer); }
void CDECL wined3d_device_context_draw(struct wined3d_device_context *context, unsigned int start_vertex, diff --git a/dlls/wined3d/wined3d.spec b/dlls/wined3d/wined3d.spec index 4daf63f98cb..37c600cfc55 100644 --- a/dlls/wined3d/wined3d.spec +++ b/dlls/wined3d/wined3d.spec @@ -135,7 +135,7 @@ @ cdecl wined3d_device_context_set_shader(ptr long ptr) @ cdecl wined3d_device_context_set_shader_resource_views(ptr long long long ptr) @ cdecl wined3d_device_context_set_state(ptr ptr) -@ cdecl wined3d_device_context_set_stream_output(ptr long ptr long) +@ cdecl wined3d_device_context_set_stream_outputs(ptr ptr) @ cdecl wined3d_device_context_set_stream_source(ptr long ptr long long) @ cdecl wined3d_device_context_set_unordered_access_views(ptr long long long ptr ptr) @ cdecl wined3d_device_context_set_vertex_declaration(ptr ptr) diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index ee43a22f977..270952c936e 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -3649,12 +3649,6 @@ struct wined3d_rasterizer_state struct wine_rb_entry entry; };
-struct wined3d_stream_output -{ - struct wined3d_buffer *buffer; - UINT offset; -}; - #define LIGHTMAP_SIZE 43 #define LIGHTMAP_HASHFUNC(x) ((x) % LIGHTMAP_SIZE)
@@ -4824,8 +4818,8 @@ void wined3d_device_context_emit_set_shader(struct wined3d_device_context *conte void wined3d_device_context_emit_set_shader_resource_views(struct wined3d_device_context *context, enum wined3d_shader_type type, unsigned int start_idx, unsigned int count, struct wined3d_shader_resource_view *const *views) DECLSPEC_HIDDEN; -void wined3d_device_context_emit_set_stream_output(struct wined3d_device_context *context, unsigned int stream_idx, - struct wined3d_buffer *buffer, unsigned int offset) DECLSPEC_HIDDEN; +void wined3d_device_context_emit_set_stream_outputs(struct wined3d_device_context *context, + const struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS]) DECLSPEC_HIDDEN; void wined3d_device_context_emit_set_stream_source(struct wined3d_device_context *context, unsigned int stream_idx, struct wined3d_buffer *buffer, unsigned int offset, unsigned int stride) DECLSPEC_HIDDEN; void wined3d_device_context_emit_set_texture(struct wined3d_device_context *context, unsigned int stage, diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index d67a818b55c..028bbee8f41 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2212,6 +2212,12 @@ struct wined3d_stateblock_state struct wined3d_light_state *light_state; };
+struct wined3d_stream_output +{ + struct wined3d_buffer *buffer; + unsigned int offset; +}; + struct wined3d_parent_ops { void (__stdcall *wined3d_object_destroyed)(void *parent); @@ -2521,8 +2527,8 @@ void __cdecl wined3d_device_context_set_shader_resource_views(struct wined3d_dev enum wined3d_shader_type type, unsigned int start_idx, unsigned int count, struct wined3d_shader_resource_view *const *views); void __cdecl wined3d_device_context_set_state(struct wined3d_device_context *context, struct wined3d_state *state); -void __cdecl wined3d_device_context_set_stream_output(struct wined3d_device_context *context, unsigned int idx, - struct wined3d_buffer *buffer, unsigned int offset); +void __cdecl wined3d_device_context_set_stream_outputs(struct wined3d_device_context *context, + const struct wined3d_stream_output outputs[WINED3D_MAX_STREAM_OUTPUT_BUFFERS]); HRESULT __cdecl wined3d_device_context_set_stream_source(struct wined3d_device_context *context, unsigned int stream_idx, struct wined3d_buffer *buffer, unsigned int offset, unsigned int stride); void __cdecl wined3d_device_context_set_unordered_access_views(struct wined3d_device_context *context,