d3dcompiler/tests: Add tests for samplers.

Signed-off-by: Zebediah Figura <zfigura@codeweavers.com>
Signed-off-by: Matteo Bruni <mbruni@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Zebediah Figura 2020-08-12 19:33:40 -05:00 committed by Alexandre Julliard
parent 3e89cbc5af
commit 172048e32b
2 changed files with 327 additions and 19 deletions

View File

@ -524,6 +524,126 @@ static void test_trig(void)
release_test_context(&test_context);
}
static void test_sampling(void)
{
struct test_context test_context;
ID3D11ShaderResourceView *srv;
ID3D11SamplerState *sampler;
ID3D10Blob *ps_code = NULL;
ID3D11Texture2D *texture;
unsigned int i;
struct vec4 v;
HRESULT hr;
static const char *tests[] =
{
"sampler s;\n"
"float4 main() : COLOR\n"
"{\n"
" return tex2D(s, float2(0.5, 0.5));\n"
"}",
"SamplerState s;\n"
"float4 main() : COLOR\n"
"{\n"
" return tex2D(s, float2(0.5, 0.5));\n"
"}",
"sampler2D s;\n"
"float4 main() : COLOR\n"
"{\n"
" return tex2D(s, float2(0.5, 0.5));\n"
"}",
"sampler s;\n"
"Texture2D t;\n"
"float4 main() : COLOR\n"
"{\n"
" return t.Sample(s, float2(0.5, 0.5));\n"
"}",
"SamplerState s;\n"
"Texture2D t;\n"
"float4 main() : COLOR\n"
"{\n"
" return t.Sample(s, float2(0.5, 0.5));\n"
"}",
};
static const D3D11_TEXTURE2D_DESC texture_desc =
{
.Width = 2,
.Height = 2,
.MipLevels = 1,
.ArraySize = 1,
.Format = DXGI_FORMAT_R32G32B32A32_FLOAT,
.SampleDesc.Count = 1,
.Usage = D3D11_USAGE_DEFAULT,
.BindFlags = D3D11_BIND_SHADER_RESOURCE,
};
static const float texture_data[] =
{
0.0f, 0.0f, 0.0f, 0.0f,
0.0f, 0.0f, 0.0f, 0.0f,
0.0f, 0.0f, 0.0f, 0.0f,
1.0f, 0.0f, 1.0f, 0.0f,
};
static const D3D11_SUBRESOURCE_DATA resource_data = {&texture_data, sizeof(texture_data) / 2};
static const D3D11_SHADER_RESOURCE_VIEW_DESC srv_desc =
{
.Format = DXGI_FORMAT_R32G32B32A32_FLOAT,
.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D,
.Texture2D.MipLevels = 1,
};
static const D3D11_SAMPLER_DESC sampler_desc =
{
.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR,
.AddressU = D3D11_TEXTURE_ADDRESS_WRAP,
.AddressV = D3D11_TEXTURE_ADDRESS_WRAP,
.AddressW = D3D11_TEXTURE_ADDRESS_WRAP,
};
static const float red[] = {1.0f, 0.0f, 0.0f, 1.0f};
if (!init_test_context(&test_context))
return;
hr = ID3D11Device_CreateTexture2D(test_context.device, &texture_desc, &resource_data, &texture);
ok(hr == S_OK, "Failed to create texture, hr %#x.\n", hr);
hr = ID3D11Device_CreateShaderResourceView(test_context.device, (ID3D11Resource *)texture, &srv_desc, &srv);
ok(hr == S_OK, "Failed to create SRV, hr %#x.\n", hr);
ID3D11DeviceContext_PSSetShaderResources(test_context.immediate_context, 0, 1, &srv);
hr = ID3D11Device_CreateSamplerState(test_context.device, &sampler_desc, &sampler);
ok(hr == S_OK, "Failed to create sampler, hr %#x.\n", hr);
ID3D11DeviceContext_PSSetSamplers(test_context.immediate_context, 0, 1, &sampler);
for (i = 0; i < ARRAY_SIZE(tests); ++i)
{
ID3D11DeviceContext_ClearRenderTargetView(test_context.immediate_context, test_context.rtv, red);
todo_wine ps_code = compile_shader_flags(tests[i], "ps_4_0", D3DCOMPILE_ENABLE_BACKWARDS_COMPATIBILITY);
if (ps_code)
{
draw_quad(&test_context, ps_code);
v = get_color_vec4(&test_context, 0, 0);
todo_wine ok(compare_vec4(&v, 0.25f, 0.0f, 0.25f, 0.0f, 0),
"Test %u: Got unexpected value {%.8e, %.8e, %.8e, %.8e}.\n", i, v.x, v.y, v.z, v.w);
ID3D10Blob_Release(ps_code);
}
}
ID3D11Texture2D_Release(texture);
ID3D11SamplerState_Release(sampler);
ID3D11ShaderResourceView_Release(srv);
release_test_context(&test_context);
}
static void check_type_desc(const char *prefix, const D3D11_SHADER_TYPE_DESC *type,
const D3D11_SHADER_TYPE_DESC *expect)
{
@ -537,6 +657,19 @@ static void check_type_desc(const char *prefix, const D3D11_SHADER_TYPE_DESC *ty
ok(!strcmp(type->Name, expect->Name), "%s: got name %s.\n", prefix, debugstr_a(type->Name));
}
static void check_resource_binding(const char *prefix, const D3D11_SHADER_INPUT_BIND_DESC *desc,
const D3D11_SHADER_INPUT_BIND_DESC *expect)
{
ok(!strcmp(desc->Name, expect->Name), "%s: got name %s.\n", prefix, debugstr_a(desc->Name));
ok(desc->Type == expect->Type, "%s: got type %#x.\n", prefix, desc->Type);
ok(desc->BindPoint == expect->BindPoint, "%s: got bind point %u.\n", prefix, desc->BindPoint);
ok(desc->BindCount == expect->BindCount, "%s: got bind count %u.\n", prefix, desc->BindCount);
ok(desc->uFlags == expect->uFlags, "%s: got flags %#x.\n", prefix, desc->uFlags);
ok(desc->ReturnType == expect->ReturnType, "%s: got return type %#x.\n", prefix, desc->ReturnType);
ok(desc->Dimension == expect->Dimension, "%s: got dimension %#x.\n", prefix, desc->Dimension);
ok(desc->NumSamples == expect->NumSamples, "%s: got multisample count %u.\n", prefix, desc->NumSamples);
}
static void test_reflection(void)
{
ID3D11ShaderReflectionConstantBuffer *cbuffer;
@ -546,8 +679,10 @@ static void test_reflection(void)
D3D11_SHADER_VARIABLE_DESC var_desc;
ID3D11ShaderReflection *reflection;
D3D11_SHADER_TYPE_DESC type_desc;
ID3D10Blob *vs_code = NULL;
D3D11_SHADER_DESC shader_desc;
ID3D10Blob *code = NULL;
unsigned int i, j, k;
char prefix[40];
ULONG refcount;
HRESULT hr;
@ -658,14 +793,55 @@ static void test_reflection(void)
{"b5", D3D_SIT_CBUFFER, 5, 1, D3D_SIF_USERPACKED},
};
todo_wine vs_code = compile_shader(vs_source, "vs_5_0");
if (!vs_code)
static const char ps_source[] =
"texture2D a;\n"
"sampler c {};\n"
"SamplerState d {};\n"
"sampler e\n"
"{\n"
" Texture = a;\n"
" foo = bar + 2;\n"
"};\n"
"SamplerState f\n"
"{\n"
" Texture = a;\n"
" foo = bar + 2;\n"
"};\n"
"sampler2D g;\n"
"sampler b : register(s5);\n"
"float4 main(float2 pos : texcoord) : SV_TARGET\n"
"{\n"
" return a.Sample(b, pos) + a.Sample(c, pos) + a.Sample(d, pos) + tex2D(f, pos) + tex2D(e, pos)"
" + tex2D(g, pos);\n"
"}";
static const D3D11_SHADER_INPUT_BIND_DESC ps_bindings[] =
{
{"c", D3D_SIT_SAMPLER, 0, 1},
{"d", D3D_SIT_SAMPLER, 1, 1},
{"e", D3D_SIT_SAMPLER, 2, 1},
{"f", D3D_SIT_SAMPLER, 3, 1},
{"g", D3D_SIT_SAMPLER, 4, 1},
{"b", D3D_SIT_SAMPLER, 5, 1, D3D_SIF_USERPACKED},
{"f", D3D_SIT_TEXTURE, 0, 1, D3D_SIF_TEXTURE_COMPONENTS, D3D_RETURN_TYPE_FLOAT, D3D_SRV_DIMENSION_TEXTURE2D, ~0u},
{"e", D3D_SIT_TEXTURE, 1, 1, D3D_SIF_TEXTURE_COMPONENTS, D3D_RETURN_TYPE_FLOAT, D3D_SRV_DIMENSION_TEXTURE2D, ~0u},
{"g", D3D_SIT_TEXTURE, 2, 1, D3D_SIF_TEXTURE_COMPONENTS, D3D_RETURN_TYPE_FLOAT, D3D_SRV_DIMENSION_TEXTURE2D, ~0u},
{"a", D3D_SIT_TEXTURE, 3, 1, D3D_SIF_TEXTURE_COMPONENTS, D3D_RETURN_TYPE_FLOAT, D3D_SRV_DIMENSION_TEXTURE2D, ~0u},
};
todo_wine code = compile_shader(vs_source, "vs_5_0");
if (!code)
return;
hr = pD3DReflect(ID3D10Blob_GetBufferPointer(vs_code), ID3D10Blob_GetBufferSize(vs_code),
hr = pD3DReflect(ID3D10Blob_GetBufferPointer(code), ID3D10Blob_GetBufferSize(code),
&IID_ID3D11ShaderReflection, (void **)&reflection);
ok(hr == S_OK, "Got hr %#x.\n", hr);
hr = reflection->lpVtbl->GetDesc(reflection, &shader_desc);
ok(hr == S_OK, "Got hr %#x.\n", hr);
ok(shader_desc.ConstantBuffers == ARRAY_SIZE(vs_buffers), "Got %u buffers.\n", shader_desc.ConstantBuffers);
ok(shader_desc.BoundResources == ARRAY_SIZE(vs_bindings), "Got %u resources.\n", shader_desc.BoundResources);
for (i = 0; i < ARRAY_SIZE(vs_buffers); ++i)
{
cbuffer = reflection->lpVtbl->GetConstantBufferByIndex(reflection, i);
@ -682,7 +858,6 @@ static void test_reflection(void)
for (j = 0; j < buffer_desc.Variables; ++j)
{
const struct shader_variable *expect = &vs_buffers[i].vars[j];
char prefix[40];
var = cbuffer->lpVtbl->GetVariableByIndex(cbuffer, j);
hr = var->lpVtbl->GetDesc(var, &var_desc);
@ -717,20 +892,36 @@ static void test_reflection(void)
D3D11_SHADER_INPUT_BIND_DESC desc;
hr = reflection->lpVtbl->GetResourceBindingDesc(reflection, i, &desc);
todo_wine ok(hr == S_OK, "Test %u: got hr %#x.\n", i, hr);
if (hr != S_OK)
break;
ok(!strcmp(desc.Name, vs_bindings[i].Name), "Test %u: got name %s.\n", i, debugstr_a(desc.Name));
ok(desc.Type == vs_bindings[i].Type, "Test %u: got type %#x.\n", i, desc.Type);
ok(desc.BindPoint == vs_bindings[i].BindPoint, "Test %u: got bind point %u.\n", i, desc.BindPoint);
ok(desc.BindCount == vs_bindings[i].BindCount, "Test %u: got bind count %u.\n", i, desc.BindCount);
ok(desc.uFlags == vs_bindings[i].uFlags, "Test %u: got flags %#x.\n", i, desc.uFlags);
ok(desc.ReturnType == vs_bindings[i].ReturnType, "Test %u: got return type %#x.\n", i, desc.ReturnType);
ok(desc.Dimension == vs_bindings[i].Dimension, "Test %u: got dimension %#x.\n", i, desc.Dimension);
ok(desc.NumSamples == vs_bindings[i].NumSamples, "Test %u: got multisample count %u.\n", i, desc.NumSamples);
ok(hr == S_OK, "Test %u: got hr %#x.\n", i, hr);
sprintf(prefix, "Test %u", i);
check_resource_binding(prefix, &desc, &vs_bindings[i]);
}
ID3D10Blob_Release(vs_code);
ID3D10Blob_Release(code);
refcount = reflection->lpVtbl->Release(reflection);
ok(!refcount, "Got unexpected refcount %u.\n", refcount);
code = compile_shader_flags(ps_source, "ps_4_0", D3DCOMPILE_ENABLE_BACKWARDS_COMPATIBILITY);
hr = pD3DReflect(ID3D10Blob_GetBufferPointer(code), ID3D10Blob_GetBufferSize(code),
&IID_ID3D11ShaderReflection, (void **)&reflection);
ok(hr == S_OK, "Got hr %#x.\n", hr);
hr = reflection->lpVtbl->GetDesc(reflection, &shader_desc);
ok(hr == S_OK, "Got hr %#x.\n", hr);
ok(!shader_desc.ConstantBuffers, "Got %u buffers.\n", shader_desc.ConstantBuffers);
ok(shader_desc.BoundResources == ARRAY_SIZE(ps_bindings), "Got %u resources.\n", shader_desc.BoundResources);
for (i = 0; i < shader_desc.BoundResources; ++i)
{
D3D11_SHADER_INPUT_BIND_DESC desc;
hr = reflection->lpVtbl->GetResourceBindingDesc(reflection, i, &desc);
ok(hr == S_OK, "Test %u: got hr %#x.\n", i, hr);
sprintf(prefix, "Test %u", i);
check_resource_binding(prefix, &desc, &ps_bindings[i]);
}
ID3D10Blob_Release(code);
refcount = reflection->lpVtbl->Release(reflection);
ok(!refcount, "Got unexpected refcount %u.\n", refcount);
}
@ -1006,4 +1197,5 @@ START_TEST(hlsl_d3d11)
test_math();
test_conditionals();
test_trig();
test_sampling();
}

View File

@ -1054,11 +1054,98 @@ static void test_global_initializer(void)
release_test_context(&test_context);
}
static void test_samplers(void)
{
struct test_context test_context;
IDirect3DTexture9 *texture;
ID3D10Blob *ps_code = NULL;
D3DLOCKED_RECT map_desc;
unsigned int i;
struct vec4 v;
HRESULT hr;
static const char *tests[] =
{
"sampler s;\n"
"float4 main() : COLOR\n"
"{\n"
" return tex2D(s, float2(0.5, 0.5));\n"
"}",
"SamplerState s;\n"
"float4 main() : COLOR\n"
"{\n"
" return tex2D(s, float2(0.5, 0.5));\n"
"}",
"sampler2D s;\n"
"float4 main() : COLOR\n"
"{\n"
" return tex2D(s, float2(0.5, 0.5));\n"
"}",
"sampler s;\n"
"Texture2D t;\n"
"float4 main() : COLOR\n"
"{\n"
" return t.Sample(s, float2(0.5, 0.5));\n"
"}",
"SamplerState s;\n"
"Texture2D t;\n"
"float4 main() : COLOR\n"
"{\n"
" return t.Sample(s, float2(0.5, 0.5));\n"
"}",
};
if (!init_test_context(&test_context))
return;
hr = IDirect3DDevice9_CreateTexture(test_context.device, 2, 2, 1, D3DUSAGE_DYNAMIC,
D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &texture, NULL);
ok(hr == D3D_OK, "Failed to create texture, hr %#x.\n", hr);
hr = IDirect3DTexture9_LockRect(texture, 0, &map_desc, NULL, D3DLOCK_DISCARD);
ok(hr == D3D_OK, "Failed to map texture, hr %#x.\n", hr);
memset(map_desc.pBits, 0, 2 * map_desc.Pitch);
((DWORD *)map_desc.pBits)[1] = 0x00ff00ff;
hr = IDirect3DTexture9_UnlockRect(texture, 0);
ok(hr == D3D_OK, "Failed to unmap texture, hr %#x.\n", hr);
hr = IDirect3DDevice9_SetTexture(test_context.device, 0, (IDirect3DBaseTexture9 *)texture);
ok(hr == D3D_OK, "Failed to set texture, hr %#x.\n", hr);
hr = IDirect3DDevice9_SetSamplerState(test_context.device, 0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR);
ok(hr == D3D_OK, "Failed to set sampler state, hr %#x.\n", hr);
for (i = 0; i < ARRAY_SIZE(tests); ++i)
{
hr = IDirect3DDevice9_Clear(test_context.device, 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(255, 0, 0), 1.0f, 0);
ok(hr == D3D_OK, "Test %u: Failed to clear, hr %#x.\n", i, hr);
todo_wine ps_code = compile_shader(tests[i], "ps_2_0");
if (ps_code)
{
draw_quad(test_context.device, ps_code);
v = get_color_vec4(test_context.device, 0, 0);
todo_wine ok(compare_vec4(&v, 0.25f, 0.0f, 0.25f, 0.0f, 128),
"Test %u: Got unexpected value {%.8e, %.8e, %.8e, %.8e}.\n", i, v.x, v.y, v.z, v.w);
ID3D10Blob_Release(ps_code);
}
}
IDirect3DTexture9_Release(texture);
release_test_context(&test_context);
}
static void check_constant_desc(const char *prefix, const D3DXCONSTANT_DESC *desc,
const D3DXCONSTANT_DESC *expect, BOOL nonzero_defaultvalue)
{
ok(!strcmp(desc->Name, expect->Name), "%s: got Name %s.\n", prefix, debugstr_a(desc->Name));
ok(desc->RegisterSet == expect->RegisterSet, "%s: got RegisterSet %#x.\n", prefix, desc->RegisterSet);
if (desc->RegisterSet == D3DXRS_SAMPLER)
ok(desc->RegisterIndex == expect->RegisterIndex, "%s: got RegisterIndex %u.\n", prefix, desc->RegisterIndex);
ok(desc->RegisterCount == expect->RegisterCount, "%s: got RegisterCount %u.\n", prefix, desc->RegisterCount);
ok(desc->Class == expect->Class, "%s: got Class %#x.\n", prefix, desc->Class);
ok(desc->Type == expect->Type, "%s: got Type %#x.\n", prefix, desc->Type);
@ -1093,9 +1180,28 @@ static void test_constant_table(void)
"uniform matrix_t i;\n"
"uniform struct matrix_record j;\n"
"uniform matrix<float,3,1> k;\n"
"float4 main(uniform float4 h) : COLOR\n"
"sampler l : register(s5);\n"
"sampler m {};\n"
"texture dummy_texture;\n"
"sampler n\n"
"{\n"
" return a + b + c._31 + d._31 + f.d._22 + g[e].x + h + i._33 + j.a._33 + k._31;\n"
" Texture = dummy_texture;\n"
" foo = bar + 2;\n"
"};\n"
"SamplerState o\n"
"{\n"
" Texture = dummy_texture;\n"
" foo = bar + 2;\n"
"};\n"
"texture2D p;\n"
"sampler q : register(s7);\n"
"SamplerState r : register(s8);\n"
"sampler2D s;\n"
"float4 main(uniform float4 h, sampler t, uniform sampler u) : COLOR\n"
"{\n"
" return b + c._31 + d._31 + f.d._22 + tex2D(l, g[e]) + tex3D(m, h.xyz) + i._33 + j.a._33 + k._31\n"
" + tex2D(n, a.xy) + tex2D(o, a.xy) + p.Sample(r, a.xy) + p.Sample(q, a.xy) + tex2D(s, a.xy)\n"
" + tex2D(t, a.xy) + tex2D(u, a.xy);\n"
"}";
D3DXCONSTANTTABLE_DESC table_desc;
@ -1110,6 +1216,7 @@ static void test_constant_table(void)
static const D3DXCONSTANT_DESC expect_constants[] =
{
{"$h", D3DXRS_FLOAT4, 0, 1, D3DXPC_VECTOR, D3DXPT_FLOAT, 1, 4, 1, 0, 16},
{"$u", D3DXRS_SAMPLER, 10, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER2D, 1, 1, 1, 0, 4},
{"a", D3DXRS_FLOAT4, 0, 1, D3DXPC_VECTOR, D3DXPT_FLOAT, 1, 4, 1, 0, 16},
{"b", D3DXRS_FLOAT4, 0, 1, D3DXPC_SCALAR, D3DXPT_FLOAT, 1, 1, 1, 0, 4},
{"c", D3DXRS_FLOAT4, 0, 1, D3DXPC_MATRIX_COLUMNS, D3DXPT_FLOAT, 3, 1, 1, 0, 12},
@ -1120,6 +1227,14 @@ static void test_constant_table(void)
{"i", D3DXRS_FLOAT4, 0, 3, D3DXPC_MATRIX_ROWS, D3DXPT_FLOAT, 3, 3, 1, 0, 36},
{"j", D3DXRS_FLOAT4, 0, 3, D3DXPC_STRUCT, D3DXPT_VOID, 1, 9, 1, 1, 36},
{"k", D3DXRS_FLOAT4, 0, 3, D3DXPC_MATRIX_ROWS, D3DXPT_FLOAT, 3, 1, 1, 0, 12},
{"l", D3DXRS_SAMPLER, 5, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER2D, 1, 1, 1, 0, 4},
{"m", D3DXRS_SAMPLER, 2, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER3D, 1, 1, 1, 0, 4},
{"n", D3DXRS_SAMPLER, 3, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER2D, 1, 1, 1, 0, 4},
{"o", D3DXRS_SAMPLER, 4, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER2D, 1, 1, 1, 0, 4},
{"q+p", D3DXRS_SAMPLER, 0, 1, D3DXPC_OBJECT, D3DXPT_TEXTURE2D, 1, 4, 1, 0, 16},
{"r+p", D3DXRS_SAMPLER, 1, 1, D3DXPC_OBJECT, D3DXPT_TEXTURE2D, 1, 4, 1, 0, 16},
{"s", D3DXRS_SAMPLER, 6, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER2D, 1, 1, 1, 0, 4},
{"t", D3DXRS_SAMPLER, 9, 1, D3DXPC_OBJECT, D3DXPT_SAMPLER2D, 1, 1, 1, 0, 4},
};
static const D3DXCONSTANT_DESC expect_fields_f[] =
@ -1604,6 +1719,7 @@ START_TEST(hlsl_d3d9)
test_struct_assignment();
test_struct_semantics();
test_global_initializer();
test_samplers();
test_constant_table();
test_fail();