d3d11: Add initial implementation of SwapDeviceContextState.

Signed-off-by: Rémi Bernon <rbernon@codeweavers.com>
Signed-off-by: Henri Verbeet <hverbeet@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Rémi Bernon 2021-01-26 12:14:26 +01:00 committed by Alexandre Julliard
parent 846276f3ca
commit b85af44374
4 changed files with 116 additions and 19 deletions

View File

@ -137,6 +137,7 @@ HRESULT WINAPI D3D11CoreCreateDevice(IDXGIFactory *factory, IDXGIAdapter *adapte
return E_FAIL;
}
d3d_device->d3d11_only = TRUE;
d3d_device->emulated_interface = IID_ID3D11Device2;
return S_OK;
}

View File

@ -551,6 +551,7 @@ struct d3d_device
D3D_FEATURE_LEVEL feature_level;
BOOL d3d11_only;
GUID emulated_interface;
struct d3d11_immediate_context immediate_context;

View File

@ -29,6 +29,12 @@ static const struct wined3d_parent_ops d3d_null_wined3d_parent_ops =
d3d_null_wined3d_object_destroyed,
};
static inline BOOL d3d_device_is_d3d10_active(struct d3d_device *device)
{
return IsEqualGUID(&device->emulated_interface, &IID_ID3D10Device)
|| IsEqualGUID(&device->emulated_interface, &IID_ID3D10Device1);
}
/* ID3DDeviceContextState methods */
static inline struct d3d_device_context_state *impl_from_ID3DDeviceContextState(ID3DDeviceContextState *iface)
@ -2672,7 +2678,29 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_CSGetConstantBuffers1(ID3D
static void STDMETHODCALLTYPE d3d11_immediate_context_SwapDeviceContextState(ID3D11DeviceContext1 *iface,
ID3DDeviceContextState *state, ID3DDeviceContextState **prev_state)
{
FIXME("iface %p, state %p, prev_state %p stub!\n", iface, state, prev_state);
struct d3d_device_context_state *state_impl;
struct d3d_device *device = device_from_immediate_ID3D11DeviceContext1(iface);
FIXME("iface %p, state %p, prev_state %p semi-stub!\n", iface, state, prev_state);
wined3d_mutex_lock();
if (prev_state)
{
*prev_state = NULL;
if ((state_impl = heap_alloc(sizeof(*state_impl))))
{
d3d_device_context_state_init(state_impl, device, &device->emulated_interface);
*prev_state = &state_impl->ID3DDeviceContextState_iface;
}
}
if ((state_impl = impl_from_ID3DDeviceContextState(state)))
{
device->emulated_interface = state_impl->emulated_interface;
if (d3d_device_is_d3d10_active(device))
FIXME("D3D10 interface emulation not fully implemented yet!\n");
}
wined3d_mutex_unlock();
}
static void STDMETHODCALLTYPE d3d11_immediate_context_ClearView(ID3D11DeviceContext1 *iface, ID3D11View *view,
@ -6373,6 +6401,7 @@ void d3d_device_init(struct d3d_device *device, void *outer_unknown)
/* COM aggregation always takes place */
device->outer_unk = outer_unknown;
device->d3d11_only = FALSE;
device->emulated_interface = GUID_NULL;
d3d11_immediate_context_init(&device->immediate_context, device);
ID3D11DeviceContext1_Release(&device->immediate_context.ID3D11DeviceContext1_iface);

View File

@ -6704,19 +6704,6 @@ static void test_device_context_state(void)
check_interface(device, &IID_ID3D11Device, TRUE, FALSE);
check_interface(device, &IID_ID3D11Device1, TRUE, FALSE);
refcount = ID3DDeviceContextState_Release(context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
feature_level = min(feature_level, D3D_FEATURE_LEVEL_10_1);
hr = ID3D11Device1_CreateDeviceContextState(device, 0, &feature_level, 1, D3D11_SDK_VERSION,
&IID_ID3D10Device, NULL, &context_state);
ok(SUCCEEDED(hr), "Failed to create device context state, hr %#x.\n", hr);
refcount = get_refcount(context_state);
ok(refcount == 1, "Got refcount %u, expected 1.\n", refcount);
context_type = ID3D11DeviceContext1_GetType(context);
ok(context_type == D3D11_DEVICE_CONTEXT_IMMEDIATE, "Unexpected context type %u.\n", context_type);
cb = create_buffer((ID3D11Device *)device, D3D11_BIND_CONSTANT_BUFFER, sizeof(constant), NULL);
ID3D11DeviceContext1_CSSetConstantBuffers(context, 0, 1, &cb);
@ -6755,12 +6742,93 @@ static void test_device_context_state(void)
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
previous_context_state = NULL;
ID3D11DeviceContext1_SwapDeviceContextState(context, context_state, &previous_context_state);
refcount = ID3DDeviceContextState_Release(context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
ok(previous_context_state != NULL, "Failed to get previous context state\n");
context_type = ID3D11DeviceContext1_GetType(context);
ok(context_type == D3D11_DEVICE_CONTEXT_IMMEDIATE, "Unexpected context type %u.\n", context_type);
ID3D11DeviceContext1_SwapDeviceContextState(context, previous_context_state, &context_state);
refcount = ID3DDeviceContextState_Release(context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
refcount = ID3DDeviceContextState_Release(previous_context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
/* ID3DDeviceContextState retains the previous state. */
tmp_sampler = (ID3D11SamplerState *)0xdeadbeef;
ID3D11DeviceContext1_VSGetSamplers(context, 0, 1, &tmp_sampler);
ok(tmp_sampler == sampler, "Got sampler %p, expected %p.\n", tmp_sampler, sampler);
ID3D11SamplerState_Release(tmp_sampler);
tmp_cb = (ID3D11Buffer *)0xdeadbeef;
ID3D11DeviceContext1_VSGetConstantBuffers(context, 0, 1, &tmp_cb);
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
tmp_sampler = (ID3D11SamplerState *)0xdeadbeef;
ID3D11DeviceContext1_GSGetSamplers(context, 0, 1, &tmp_sampler);
ok(tmp_sampler == sampler, "Got sampler %p, expected %p.\n", tmp_sampler, sampler);
ID3D11SamplerState_Release(tmp_sampler);
tmp_cb = (ID3D11Buffer *)0xdeadbeef;
ID3D11DeviceContext1_GSGetConstantBuffers(context, 0, 1, &tmp_cb);
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
tmp_sampler = (ID3D11SamplerState *)0xdeadbeef;
ID3D11DeviceContext1_PSGetSamplers(context, 0, 1, &tmp_sampler);
ok(tmp_sampler == sampler, "Got sampler %p, expected %p.\n", tmp_sampler, sampler);
ID3D11SamplerState_Release(tmp_sampler);
tmp_cb = (ID3D11Buffer *)0xdeadbeef;
ID3D11DeviceContext1_PSGetConstantBuffers(context, 0, 1, &tmp_cb);
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
tmp_sampler = (ID3D11SamplerState *)0xdeadbeef;
ID3D11DeviceContext1_HSGetSamplers(context, 0, 1, &tmp_sampler);
ok(tmp_sampler == sampler, "Got sampler %p, expected %p.\n", tmp_sampler, sampler);
ID3D11SamplerState_Release(tmp_sampler);
tmp_cb = (ID3D11Buffer *)0xdeadbeef;
ID3D11DeviceContext1_HSGetConstantBuffers(context, 0, 1, &tmp_cb);
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
tmp_sampler = (ID3D11SamplerState *)0xdeadbeef;
ID3D11DeviceContext1_DSGetSamplers(context, 0, 1, &tmp_sampler);
ok(tmp_sampler == sampler, "Got sampler %p, expected %p.\n", tmp_sampler, sampler);
ID3D11SamplerState_Release(tmp_sampler);
tmp_cb = (ID3D11Buffer *)0xdeadbeef;
ID3D11DeviceContext1_DSGetConstantBuffers(context, 0, 1, &tmp_cb);
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
tmp_sampler = (ID3D11SamplerState *)0xdeadbeef;
ID3D11DeviceContext1_CSGetSamplers(context, 0, 1, &tmp_sampler);
ok(tmp_sampler == sampler, "Got sampler %p, expected %p.\n", tmp_sampler, sampler);
ID3D11SamplerState_Release(tmp_sampler);
tmp_cb = (ID3D11Buffer *)0xdeadbeef;
ID3D11DeviceContext1_CSGetConstantBuffers(context, 0, 1, &tmp_cb);
ok(tmp_cb == cb, "Got buffer %p, expected %p.\n", tmp_cb, cb);
ID3D11Buffer_Release(tmp_cb);
feature_level = min(feature_level, D3D_FEATURE_LEVEL_10_1);
hr = ID3D11Device1_CreateDeviceContextState(device, 0, &feature_level, 1, D3D11_SDK_VERSION,
&IID_ID3D10Device, NULL, &context_state);
ok(SUCCEEDED(hr), "Failed to create device context state, hr %#x.\n", hr);
refcount = get_refcount(context_state);
ok(refcount == 1, "Got refcount %u, expected 1.\n", refcount);
context_type = ID3D11DeviceContext1_GetType(context);
ok(context_type == D3D11_DEVICE_CONTEXT_IMMEDIATE, "Unexpected context type %u.\n", context_type);
/* Enable ID3D10Device behavior. */
previous_context_state = NULL;
ID3D11DeviceContext1_SwapDeviceContextState(context, context_state, &previous_context_state);
refcount = ID3DDeviceContextState_Release(context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
todo_wine ok(previous_context_state != NULL, "Failed to get previous context state\n");
ok(previous_context_state != NULL, "Failed to get previous context state\n");
context_type = ID3D11DeviceContext1_GetType(context);
ok(context_type == D3D11_DEVICE_CONTEXT_IMMEDIATE, "Unexpected context type %u.\n", context_type);
@ -6839,11 +6907,9 @@ static void test_device_context_state(void)
context_state = NULL;
ID3D11DeviceContext1_SwapDeviceContextState(context, previous_context_state, &context_state);
if (!context_state) refcount = 0;
else refcount = ID3DDeviceContextState_Release(context_state);
refcount = ID3DDeviceContextState_Release(context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
if (!previous_context_state) refcount = 0;
else refcount = ID3DDeviceContextState_Release(previous_context_state);
refcount = ID3DDeviceContextState_Release(previous_context_state);
ok(!refcount, "Got refcount %u, expected 0.\n", refcount);
/* ID3DDeviceContextState retains the previous state. */