Files
wine-staging/patches/vkd3d-latest/0001-Updated-vkd3d-to-e69f3da089d472b723b016ef67c04c0f954.patch
Alistair Leslie-Hughes 815194acd6 Updated vkd3d-latest patchset
2025-10-01 07:52:38 +10:00

8557 lines
388 KiB
Diff

From 6539b8d0685337b99debbe678354c3a9a58747d7 Mon Sep 17 00:00:00 2001
From: Alistair Leslie-Hughes <leslie_alistair@hotmail.com>
Date: Mon, 26 May 2025 07:03:34 +1000
Subject: [PATCH] Updated vkd3d to e69f3da089d472b723b016ef67c04c0f954fa792.
---
dlls/msado15/tests/msado15.c | 2 +-
libs/vkd3d/include/private/spirv_grammar.h | 561 +-------
libs/vkd3d/include/private/vkd3d_common.h | 4 +-
libs/vkd3d/include/private/vkd3d_version.h | 2 +-
libs/vkd3d/include/vkd3d_shader.h | 38 +-
libs/vkd3d/libs/vkd3d-common/blob.c | 1 +
libs/vkd3d/libs/vkd3d-shader/d3d_asm.c | 46 +-
libs/vkd3d/libs/vkd3d-shader/d3dbc.c | 36 +-
libs/vkd3d/libs/vkd3d-shader/dxil.c | 151 ++-
libs/vkd3d/libs/vkd3d-shader/fx.c | 2 +-
libs/vkd3d/libs/vkd3d-shader/glsl.c | 74 +-
libs/vkd3d/libs/vkd3d-shader/hlsl.c | 70 +
libs/vkd3d/libs/vkd3d-shader/hlsl.h | 16 +-
libs/vkd3d/libs/vkd3d-shader/hlsl.l | 2 +-
libs/vkd3d/libs/vkd3d-shader/hlsl.y | 60 +-
libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c | 752 ++++++++---
.../libs/vkd3d-shader/hlsl_constant_ops.c | 243 ++--
libs/vkd3d/libs/vkd3d-shader/ir.c | 1132 ++++++++++-------
libs/vkd3d/libs/vkd3d-shader/msl.c | 45 +-
libs/vkd3d/libs/vkd3d-shader/preproc.l | 13 +-
libs/vkd3d/libs/vkd3d-shader/spirv.c | 319 ++---
libs/vkd3d/libs/vkd3d-shader/tpf.c | 43 +-
.../libs/vkd3d-shader/vkd3d_shader_main.c | 222 +---
.../libs/vkd3d-shader/vkd3d_shader_private.h | 94 +-
.../vkd3d/libs/vkd3d-utils/vkd3d_utils_main.c | 17 +-
libs/vkd3d/libs/vkd3d/command.c | 2 +-
libs/vkd3d/libs/vkd3d/state.c | 6 +-
libs/vkd3d/libs/vkd3d/utils.c | 3 +-
28 files changed, 2184 insertions(+), 1772 deletions(-)
diff --git a/dlls/msado15/tests/msado15.c b/dlls/msado15/tests/msado15.c
index 03eaab92b39..3f4b55d2916 100644
--- a/dlls/msado15/tests/msado15.c
+++ b/dlls/msado15/tests/msado15.c
@@ -2023,8 +2023,8 @@ START_TEST(msado15)
setup_database();
test_Connection();
- test_Connection_Open();
test_ConnectionPoint();
+ test_Connection_Open();
test_ADORecordsetConstruction(FALSE);
test_ADORecordsetConstruction(TRUE);
test_Fields();
diff --git a/libs/vkd3d/include/private/spirv_grammar.h b/libs/vkd3d/include/private/spirv_grammar.h
index 34cadd9bd58..2aac5a6558c 100644
--- a/libs/vkd3d/include/private/spirv_grammar.h
+++ b/libs/vkd3d/include/private/spirv_grammar.h
@@ -43,12 +43,10 @@ enum spirv_parser_operand_type
SPIRV_PARSER_OPERAND_TYPE_ADDRESSING_MODEL,
SPIRV_PARSER_OPERAND_TYPE_BUILT_IN,
SPIRV_PARSER_OPERAND_TYPE_CAPABILITY,
- SPIRV_PARSER_OPERAND_TYPE_COMPONENT_TYPE,
SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_LAYOUT,
SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_OPERANDS,
SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_REDUCE,
SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_USE,
- SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_VECTOR_MATRIX_LAYOUT,
SPIRV_PARSER_OPERAND_TYPE_DECORATION,
SPIRV_PARSER_OPERAND_TYPE_DIM,
SPIRV_PARSER_OPERAND_TYPE_EXECUTION_MODE,
@@ -84,7 +82,6 @@ enum spirv_parser_operand_type
SPIRV_PARSER_OPERAND_TYPE_LITERAL_STRING,
SPIRV_PARSER_OPERAND_TYPE_LOAD_CACHE_CONTROL,
SPIRV_PARSER_OPERAND_TYPE_LOOP_CONTROL,
- SPIRV_PARSER_OPERAND_TYPE_MATRIX_MULTIPLY_ACCUMULATE_OPERANDS,
SPIRV_PARSER_OPERAND_TYPE_MEMORY_ACCESS,
SPIRV_PARSER_OPERAND_TYPE_MEMORY_MODEL,
SPIRV_PARSER_OPERAND_TYPE_MEMORY_SEMANTICS,
@@ -149,7 +146,7 @@ spirv_parser_operand_type_info[] =
},
[SPIRV_PARSER_OPERAND_TYPE_BUILT_IN] =
{
- "BuiltIn", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 126,
+ "BuiltIn", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 116,
(struct spirv_parser_enumerant[])
{
{0, "Position"},
@@ -210,9 +207,6 @@ spirv_parser_operand_type_info[] =
{0x1156, "DeviceIndex"},
{0x1158, "ViewIndex"},
{0x115c, "ShadingRateKHR"},
- {0x118c, "TileOffsetQCOM"},
- {0x118d, "TileDimensionQCOM"},
- {0x118e, "TileApronSizeQCOM"},
{0x1380, "BaryCoordNoPerspAMD"},
{0x1381, "BaryCoordNoPerspCentroidAMD"},
{0x1382, "BaryCoordNoPerspSampleAMD"},
@@ -264,25 +258,18 @@ spirv_parser_operand_type_info[] =
{0x14e0, "HitMicroTriangleVertexBarycentricsNV"},
{0x14e7, "IncomingRayFlagsKHR"},
{0x14e8, "RayGeometryIndexKHR"},
- {0x14ef, "HitIsSphereNV"},
- {0x14f0, "HitIsLSSNV"},
- {0x14f1, "HitSpherePositionNV"},
{0x14fe, "WarpsPerSMNV"},
{0x14ff, "SMCountNV"},
{0x1500, "WarpIDNV"},
{0x1501, "SMIDNV"},
- {0x1514, "HitLSSPositionsNV"},
{0x151d, "HitKindFrontFacingMicroTriangleNV"},
{0x151e, "HitKindBackFacingMicroTriangleNV"},
- {0x152c, "HitSphereRadiusNV"},
- {0x152d, "HitLSSRadiiNV"},
- {0x153c, "ClusterIDNV"},
{0x1785, "CullMaskKHR"},
}
},
[SPIRV_PARSER_OPERAND_TYPE_CAPABILITY] =
{
- "Capability", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 261,
+ "Capability", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 245,
(struct spirv_parser_enumerant[])
{
{0, "Matrix"},
@@ -393,7 +380,6 @@ spirv_parser_operand_type_info[] =
{0x1184, "TextureSampleWeightedQCOM"},
{0x1185, "TextureBoxFilterQCOM"},
{0x1186, "TextureBlockMatchQCOM"},
- {0x118f, "TileShadingQCOM"},
{0x1192, "TextureBlockMatch2QCOM"},
{0x1390, "Float16ImageAMD"},
{0x1391, "ImageGatherBiasLodAMD"},
@@ -404,9 +390,6 @@ spirv_parser_operand_type_info[] =
{0x13bf, "ShaderClockKHR"},
{0x13cb, "ShaderEnqueueAMDX"},
{0x13df, "QuadControlKHR"},
- {0x13fc, "BFloat16TypeKHR"},
- {0x13fd, "BFloat16DotProductKHR"},
- {0x13fe, "BFloat16CooperativeMatrixKHR"},
{0x1481, "SampleMaskOverrideCoverageNV"},
{0x1483, "GeometryShaderPassthroughNV"},
{0x1486, "ShaderViewportIndexLayerEXT"},
@@ -452,19 +435,14 @@ spirv_parser_operand_type_info[] =
{0x1507, "ShaderInvocationReorderNV"},
{0x150e, "BindlessTextureNV"},
{0x150f, "RayQueryPositionFetchKHR"},
- {0x1512, "CooperativeVectorNV"},
{0x151c, "AtomicFloat16VectorNV"},
{0x1521, "RayTracingDisplacementMicromapNV"},
{0x1526, "RawAccessChainsNV"},
- {0x152a, "RayTracingSpheresGeometryNV"},
- {0x152b, "RayTracingLinearSweptSpheresGeometryNV"},
{0x1536, "CooperativeMatrixReductionsNV"},
{0x1537, "CooperativeMatrixConversionsNV"},
{0x1538, "CooperativeMatrixPerElementOperationsNV"},
{0x1539, "CooperativeMatrixTensorAddressingNV"},
{0x153a, "CooperativeMatrixBlockLoadsNV"},
- {0x153b, "CooperativeVectorTrainingNV"},
- {0x153d, "RayTracingClusterAccelerationStructureNV"},
{0x153f, "TensorAddressingNV"},
{0x15c0, "SubgroupShuffleINTEL"},
{0x15c1, "SubgroupBufferBlockIOINTEL"},
@@ -529,47 +507,18 @@ spirv_parser_operand_type_info[] =
{0x1800, "ArithmeticFenceEXT"},
{0x1806, "FPGAClusterAttributesV2INTEL"},
{0x1811, "FPGAKernelAttributesv2INTEL"},
- {0x1812, "TaskSequenceINTEL"},
{0x1819, "FPMaxErrorINTEL"},
{0x181b, "FPGALatencyControlINTEL"},
{0x181e, "FPGAArgumentInterfacesINTEL"},
{0x182b, "GlobalVariableHostAccessINTEL"},
{0x182d, "GlobalVariableFPGADecorationsINTEL"},
{0x184c, "SubgroupBufferPrefetchINTEL"},
- {0x1854, "Subgroup2DBlockIOINTEL"},
- {0x1855, "Subgroup2DBlockTransformINTEL"},
- {0x1856, "Subgroup2DBlockTransposeINTEL"},
- {0x185c, "SubgroupMatrixMultiplyAccumulateINTEL"},
- {0x1861, "TernaryBitwiseFunctionINTEL"},
{0x1900, "GroupUniformArithmeticKHR"},
- {0x1919, "TensorFloat32RoundingINTEL"},
{0x191b, "MaskedGatherScatterINTEL"},
{0x1929, "CacheControlsINTEL"},
{0x193c, "RegisterLimitsINTEL"},
}
},
- [SPIRV_PARSER_OPERAND_TYPE_COMPONENT_TYPE] =
- {
- "ComponentType", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 15,
- (struct spirv_parser_enumerant[])
- {
- {0, "Float16NV"},
- {0x1, "Float32NV"},
- {0x2, "Float64NV"},
- {0x3, "SignedInt8NV"},
- {0x4, "SignedInt16NV"},
- {0x5, "SignedInt32NV"},
- {0x6, "SignedInt64NV"},
- {0x7, "UnsignedInt8NV"},
- {0x8, "UnsignedInt16NV"},
- {0x9, "UnsignedInt32NV"},
- {0xa, "UnsignedInt64NV"},
- {0x3ba247f8, "SignedInt8PackedNV"},
- {0x3ba247f9, "UnsignedInt8PackedNV"},
- {0x3ba247fa, "FloatE4M3NV"},
- {0x3ba247fb, "FloatE5M2NV"},
- }
- },
[SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_LAYOUT] =
{
"CooperativeMatrixLayout", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 4,
@@ -614,17 +563,6 @@ spirv_parser_operand_type_info[] =
{0x2, "MatrixAccumulatorKHR"},
}
},
- [SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_VECTOR_MATRIX_LAYOUT] =
- {
- "CooperativeVectorMatrixLayout", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 4,
- (struct spirv_parser_enumerant[])
- {
- {0, "RowMajorNV"},
- {0x1, "ColumnMajorNV"},
- {0x2, "InferencingOptimalNV"},
- {0x3, "TrainingOptimalNV"},
- }
- },
[SPIRV_PARSER_OPERAND_TYPE_DECORATION] =
{
"Decoration", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 142,
@@ -1240,7 +1178,7 @@ spirv_parser_operand_type_info[] =
},
[SPIRV_PARSER_OPERAND_TYPE_EXECUTION_MODE] =
{
- "ExecutionMode", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 96,
+ "ExecutionMode", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 94,
(struct spirv_parser_enumerant[])
{
{
@@ -1389,16 +1327,6 @@ spirv_parser_operand_type_info[] =
SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER,
}
},
- {0x1189, "NonCoherentTileAttachmentReadQCOM"},
- {
- 0x118a, "TileShadingRateQCOM", 3,
- (enum spirv_parser_operand_type[])
- {
- SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER,
- SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER,
- SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER,
- }
- },
{0x1399, "EarlyAndLateFragmentTestsAMD"},
{0x13a3, "StencilRefReplacingEXT"},
{0x13cd, "CoalescingAMDX"},
@@ -1628,11 +1556,7 @@ spirv_parser_operand_type_info[] =
},
[SPIRV_PARSER_OPERAND_TYPE_FPENCODING] =
{
- "FPEncoding", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 1,
- (struct spirv_parser_enumerant[])
- {
- {0, "BFloat16KHR"},
- }
+ "FPEncoding", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM
},
[SPIRV_PARSER_OPERAND_TYPE_FPFAST_MATH_MODE] =
{
@@ -1757,7 +1681,7 @@ spirv_parser_operand_type_info[] =
},
[SPIRV_PARSER_OPERAND_TYPE_IMAGE_CHANNEL_DATA_TYPE] =
{
- "ImageChannelDataType", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 26,
+ "ImageChannelDataType", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 20,
(struct spirv_parser_enumerant[])
{
{0, "SnormInt8"},
@@ -1777,15 +1701,9 @@ spirv_parser_operand_type_info[] =
{0xe, "Float"},
{0xf, "UnormInt24"},
{0x10, "UnormInt101010_2"},
- {0x11, "UnormInt10X6EXT"},
{0x13, "UnsignedIntRaw10EXT"},
{0x14, "UnsignedIntRaw12EXT"},
{0x15, "UnormInt2_101010EXT"},
- {0x16, "UnsignedInt10X6EXT"},
- {0x17, "UnsignedInt12X4EXT"},
- {0x18, "UnsignedInt14X2EXT"},
- {0x19, "UnormInt12X4EXT"},
- {0x1a, "UnormInt14X2EXT"},
}
},
[SPIRV_PARSER_OPERAND_TYPE_IMAGE_CHANNEL_ORDER] =
@@ -2146,28 +2064,6 @@ spirv_parser_operand_type_info[] =
},
}
},
- [SPIRV_PARSER_OPERAND_TYPE_MATRIX_MULTIPLY_ACCUMULATE_OPERANDS] =
- {
- "MatrixMultiplyAccumulateOperands", SPIRV_PARSER_OPERAND_CATEGORY_BIT_ENUM, 15,
- (struct spirv_parser_enumerant[])
- {
- {0, "None"},
- {0x1, "MatrixASignedComponentsINTEL"},
- {0x2, "MatrixBSignedComponentsINTEL"},
- {0x4, "MatrixCBFloat16INTEL"},
- {0x8, "MatrixResultBFloat16INTEL"},
- {0x10, "MatrixAPackedInt8INTEL"},
- {0x20, "MatrixBPackedInt8INTEL"},
- {0x40, "MatrixAPackedInt4INTEL"},
- {0x80, "MatrixBPackedInt4INTEL"},
- {0x100, "MatrixATF32INTEL"},
- {0x200, "MatrixBTF32INTEL"},
- {0x400, "MatrixAPackedFloat16INTEL"},
- {0x800, "MatrixBPackedFloat16INTEL"},
- {0x1000, "MatrixAPackedBFloat16INTEL"},
- {0x2000, "MatrixBPackedBFloat16INTEL"},
- }
- },
[SPIRV_PARSER_OPERAND_TYPE_MEMORY_ACCESS] =
{
"MemoryAccess", SPIRV_PARSER_OPERAND_CATEGORY_BIT_ENUM, 9,
@@ -2405,7 +2301,7 @@ spirv_parser_operand_type_info[] =
},
[SPIRV_PARSER_OPERAND_TYPE_SOURCE_LANGUAGE] =
{
- "SourceLanguage", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 14,
+ "SourceLanguage", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 13,
(struct spirv_parser_enumerant[])
{
{0, "Unknown"},
@@ -2421,12 +2317,11 @@ spirv_parser_operand_type_info[] =
{0xa, "WGSL"},
{0xb, "Slang"},
{0xc, "Zig"},
- {0xd, "Rust"},
}
},
[SPIRV_PARSER_OPERAND_TYPE_STORAGE_CLASS] =
{
- "StorageClass", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 28,
+ "StorageClass", SPIRV_PARSER_OPERAND_CATEGORY_VALUE_ENUM, 27,
(struct spirv_parser_enumerant[])
{
{0, "UniformConstant"},
@@ -2443,7 +2338,6 @@ spirv_parser_operand_type_info[] =
{0xb, "Image"},
{0xc, "StorageBuffer"},
{0x104c, "TileImageEXT"},
- {0x118b, "TileAttachmentQCOM"},
{0x13cc, "NodePayloadAMDX"},
{0x14d0, "CallableDataKHR"},
{0x14d1, "IncomingCallableDataKHR"},
@@ -6996,78 +6890,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_IMAGE_OPERANDS, '?'},
}
},
- {
- 0x14a8, "OpTypeCooperativeVectorNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x14a9, "OpCooperativeVectorMatrixMulNV", 13,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF, '?'},
- {SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_OPERANDS, '?'},
- }
- },
- {
- 0x14aa, "OpCooperativeVectorOuterProductAccumulateNV", 7,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF, '?'},
- }
- },
- {
- 0x14ab, "OpCooperativeVectorReduceSumAccumulateNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x14ac, "OpCooperativeVectorMatrixMulAddNV", 16,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF, '?'},
- {SPIRV_PARSER_OPERAND_TYPE_COOPERATIVE_MATRIX_OPERANDS, '?'},
- }
- },
{
0x14ad, "OpCooperativeMatrixConvertNV", 3,
(struct spirv_parser_instruction_operand[])
@@ -7138,27 +6960,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
}
},
- {
- 0x14b6, "OpCooperativeVectorLoadNV", 5,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_MEMORY_ACCESS, '?'},
- }
- },
- {
- 0x14b7, "OpCooperativeVectorStoreNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_MEMORY_ACCESS, '?'},
- }
- },
{
0x14d6, "OpReportIntersectionKHR", 4,
(struct spirv_parser_instruction_operand[])
@@ -7249,25 +7050,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
}
},
- {
- 0x14e1, "OpRayQueryGetClusterIdNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x14e2, "OpHitObjectGetClusterIdNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
{
0x14ee, "OpTypeCooperativeMatrixNV", 5,
(struct spirv_parser_instruction_operand[])
@@ -7580,130 +7362,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_RAW_ACCESS_CHAIN_OPERANDS, '?'},
}
},
- {
- 0x1533, "OpRayQueryGetIntersectionSpherePositionNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1534, "OpRayQueryGetIntersectionSphereRadiusNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1535, "OpRayQueryGetIntersectionLSSPositionsNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1536, "OpRayQueryGetIntersectionLSSRadiiNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1537, "OpRayQueryGetIntersectionLSSHitValueNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1538, "OpHitObjectGetSpherePositionNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1539, "OpHitObjectGetSphereRadiusNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x153a, "OpHitObjectGetLSSPositionsNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x153b, "OpHitObjectGetLSSRadiiNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x153c, "OpHitObjectIsSphereHitNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x153d, "OpHitObjectIsLSSHitNV", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x153e, "OpRayQueryIsSphereHitNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x153f, "OpRayQueryIsLSSHitNV", 4,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
{
0x15c3, "OpSubgroupShuffleINTEL", 4,
(struct spirv_parser_instruction_operand[])
@@ -7962,9 +7620,10 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x15e9, "OpAsmTargetINTEL", 2,
+ 0x15e9, "OpAsmTargetINTEL", 3,
(struct spirv_parser_instruction_operand[])
{
+ {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_STRING},
}
@@ -9237,7 +8896,7 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x16d0, "OpArbitraryFloatSinCosPiINTEL", 8,
+ 0x16d0, "OpArbitraryFloatSinCosPiINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
@@ -9248,6 +8907,7 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
+ {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
}
},
{
@@ -9279,7 +8939,7 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x16d3, "OpArbitraryFloatCastToIntINTEL", 8,
+ 0x16d3, "OpArbitraryFloatCastToIntINTEL", 7,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
@@ -9289,7 +8949,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
- {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
}
},
{
@@ -9803,7 +9462,7 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x16fa, "OpArbitraryFloatPowNINTEL", 10,
+ 0x16fa, "OpArbitraryFloatPowNINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
@@ -9815,7 +9474,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
- {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
}
},
{
@@ -9851,12 +9509,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1723, "OpFixedSqrtINTEL", 8,
+ 0x1723, "OpFixedSqrtINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9865,12 +9524,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1724, "OpFixedRecipINTEL", 8,
+ 0x1724, "OpFixedRecipINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9879,12 +9539,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1725, "OpFixedRsqrtINTEL", 8,
+ 0x1725, "OpFixedRsqrtINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9893,12 +9554,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1726, "OpFixedSinINTEL", 8,
+ 0x1726, "OpFixedSinINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9907,12 +9569,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1727, "OpFixedCosINTEL", 8,
+ 0x1727, "OpFixedCosINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9921,12 +9584,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1728, "OpFixedSinCosINTEL", 8,
+ 0x1728, "OpFixedSinCosINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9935,12 +9599,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x1729, "OpFixedSinPiINTEL", 8,
+ 0x1729, "OpFixedSinPiINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9949,12 +9614,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x172a, "OpFixedCosPiINTEL", 8,
+ 0x172a, "OpFixedCosPiINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9963,12 +9629,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x172b, "OpFixedSinCosPiINTEL", 8,
+ 0x172b, "OpFixedSinCosPiINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9977,12 +9644,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x172c, "OpFixedLogINTEL", 8,
+ 0x172c, "OpFixedLogINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -9991,12 +9659,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x172d, "OpFixedExpINTEL", 8,
+ 0x172d, "OpFixedExpINTEL", 9,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
{SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
@@ -10043,12 +9712,13 @@ spirv_parser_opcode_info[] =
}
},
{
- 0x173d, "OpFPGARegINTEL", 3,
+ 0x173d, "OpFPGARegINTEL", 4,
(struct spirv_parser_instruction_operand[])
{
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
{SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
+ {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
}
},
{
@@ -10311,50 +9981,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
}
},
- {
- 0x1813, "OpTaskSequenceCreateINTEL", 7,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
- {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
- {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
- {SPIRV_PARSER_OPERAND_TYPE_LITERAL_INTEGER},
- }
- },
- {
- 0x1814, "OpTaskSequenceAsyncINTEL", 2,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF, '*'},
- }
- },
- {
- 0x1815, "OpTaskSequenceGetINTEL", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1816, "OpTaskSequenceReleaseINTEL", 1,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1837, "OpTypeTaskSequenceINTEL", 1,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- }
- },
{
0x184d, "OpSubgroupBlockPrefetchINTEL", 3,
(struct spirv_parser_instruction_operand[])
@@ -10364,110 +9990,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_MEMORY_ACCESS, '?'},
}
},
- {
- 0x1857, "OpSubgroup2DBlockLoadINTEL", 10,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1858, "OpSubgroup2DBlockLoadTransformINTEL", 10,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x1859, "OpSubgroup2DBlockLoadTransposeINTEL", 10,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x185a, "OpSubgroup2DBlockPrefetchINTEL", 9,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x185b, "OpSubgroup2DBlockStoreINTEL", 10,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
- {
- 0x185d, "OpSubgroupMatrixMultiplyAccumulateINTEL", 7,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_MATRIX_MULTIPLY_ACCUMULATE_OPERANDS, '?'},
- }
- },
- {
- 0x1862, "OpBitwiseFunctionINTEL", 6,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
{
0x1901, "OpGroupIMulKHR", 5,
(struct spirv_parser_instruction_operand[])
@@ -10556,15 +10078,6 @@ spirv_parser_opcode_info[] =
{SPIRV_PARSER_OPERAND_TYPE_ID_REF},
}
},
- {
- 0x191a, "OpRoundFToTF32INTEL", 3,
- (struct spirv_parser_instruction_operand[])
- {
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT_TYPE},
- {SPIRV_PARSER_OPERAND_TYPE_ID_RESULT},
- {SPIRV_PARSER_OPERAND_TYPE_ID_REF},
- }
- },
{
0x191c, "OpMaskedGatherINTEL", 6,
(struct spirv_parser_instruction_operand[])
diff --git a/libs/vkd3d/include/private/vkd3d_common.h b/libs/vkd3d/include/private/vkd3d_common.h
index 08341304eea..8b63acf68e1 100644
--- a/libs/vkd3d/include/private/vkd3d_common.h
+++ b/libs/vkd3d/include/private/vkd3d_common.h
@@ -38,6 +38,8 @@
#include <intrin.h>
#endif
+#define VKD3D_SHADER_API_VERSION_CURRENT VKD3D_SHADER_API_VERSION_1_17
+
#ifndef ARRAY_SIZE
# define ARRAY_SIZE(x) (sizeof(x) / sizeof(*(x)))
#endif
@@ -279,7 +281,7 @@ static inline unsigned int vkd3d_popcount(unsigned int v)
{
#ifdef _MSC_VER
return __popcnt(v);
-#elif defined(__MINGW32__)
+#elif defined(HAVE_BUILTIN_POPCOUNT)
return __builtin_popcount(v);
#else
v -= (v >> 1) & 0x55555555;
diff --git a/libs/vkd3d/include/private/vkd3d_version.h b/libs/vkd3d/include/private/vkd3d_version.h
index 0edc4428022..687751d6a5f 100644
--- a/libs/vkd3d/include/private/vkd3d_version.h
+++ b/libs/vkd3d/include/private/vkd3d_version.h
@@ -1 +1 @@
-#define VKD3D_VCS_ID " (Wine bundled)"
+#define VKD3D_VCS_ID " (git a8ca1f95)"
diff --git a/libs/vkd3d/include/vkd3d_shader.h b/libs/vkd3d/include/vkd3d_shader.h
index d82869e79ea..3a2f54c8f22 100644
--- a/libs/vkd3d/include/vkd3d_shader.h
+++ b/libs/vkd3d/include/vkd3d_shader.h
@@ -120,6 +120,11 @@ enum vkd3d_shader_structure_type
* \since 1.15
*/
VKD3D_SHADER_STRUCTURE_TYPE_SCAN_HULL_SHADER_TESSELLATION_INFO,
+ /**
+ * The structure is a vkd3d_shader_scan_thread_group_size_info structure.
+ * \since 1.18
+ */
+ VKD3D_SHADER_STRUCTURE_TYPE_SCAN_THREAD_GROUP_SIZE_INFO,
VKD3D_FORCE_32_BIT_ENUM(VKD3D_SHADER_STRUCTURE_TYPE),
};
@@ -417,10 +422,17 @@ struct vkd3d_shader_code
{
/**
* Pointer to the code. Note that textual formats are not null-terminated.
- * Therefore \a size should not include a null terminator, when this
- * structure is passed as input to a vkd3d-shader function, and the
- * allocated string will not include a null terminator when this structure
- * is used as output.
+ * Therefore \a size should not include a null terminator when this
+ * structure is passed as input to a vkd3d-shader function, and \a size
+ * will not include a null terminator when this structure is used as
+ * output.
+ *
+ * For convenience, vkd3d_shader_preprocess() and vkd3d_shader_compile()
+ * will append a null terminator past the end of their output when
+ * outputting textual formats like VKD3D_SHADER_TARGET_D3D_ASM. This makes
+ * it safe to call functions like strlen() on \a code for such output,
+ * although doing so will obviously not account for any embedded null
+ * characters that may be present.
*/
const void *code;
/** Size of \a code, in bytes. */
@@ -2282,6 +2294,24 @@ struct vkd3d_shader_scan_hull_shader_tessellation_info
enum vkd3d_shader_tessellator_partitioning partitioning;
};
+/**
+ * A chained structure describing the thread group size in a compute shader.
+ *
+ * This structure extends vkd3d_shader_compile_info.
+ *
+ * \since 1.18
+ */
+struct vkd3d_shader_scan_thread_group_size_info
+{
+ /** Must be set to VKD3D_SHADER_STRUCTURE_TYPE_SCAN_THREAD_GROUP_SIZE_INFO. */
+ enum vkd3d_shader_structure_type type;
+ /** Optional pointer to a structure containing further parameters. */
+ const void *next;
+
+ /** The thread group size in the x/y/z direction. */
+ unsigned int x, y, z;
+};
+
/**
* Data type of a shader varying, returned as part of struct
* vkd3d_shader_signature_element.
diff --git a/libs/vkd3d/libs/vkd3d-common/blob.c b/libs/vkd3d/libs/vkd3d-common/blob.c
index f60ef7db769..c2c6ad67804 100644
--- a/libs/vkd3d/libs/vkd3d-common/blob.c
+++ b/libs/vkd3d/libs/vkd3d-common/blob.c
@@ -20,6 +20,7 @@
#define WIDL_C_INLINE_WRAPPERS
#endif
#define COBJMACROS
+
#define CONST_VTABLE
#include "vkd3d.h"
#include "vkd3d_blob.h"
diff --git a/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c b/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c
index 6425a8f62d2..e2fb8b12998 100644
--- a/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c
+++ b/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c
@@ -390,27 +390,10 @@ static void shader_print_resource_type(struct vkd3d_d3d_asm_compiler *compiler,
static void shader_print_data_type(struct vkd3d_d3d_asm_compiler *compiler, enum vsir_data_type type)
{
- static const char *const data_type_names[] =
- {
- [VSIR_DATA_BOOL ] = "bool",
- [VSIR_DATA_F16 ] = "half",
- [VSIR_DATA_F32 ] = "float",
- [VSIR_DATA_F64 ] = "double",
- [VSIR_DATA_I32 ] = "int",
- [VSIR_DATA_U8 ] = "uint8",
- [VSIR_DATA_U16 ] = "uint16",
- [VSIR_DATA_U32 ] = "uint",
- [VSIR_DATA_U64 ] = "uint64",
- [VSIR_DATA_SNORM ] = "snorm",
- [VSIR_DATA_UNORM ] = "unorm",
- [VSIR_DATA_OPAQUE ] = "opaque",
- [VSIR_DATA_MIXED ] = "mixed",
- [VSIR_DATA_CONTINUED] = "<continued>",
- [VSIR_DATA_UNUSED ] = "<unused>",
- };
+ const char *name;
- if (type < ARRAY_SIZE(data_type_names))
- vkd3d_string_buffer_printf(&compiler->buffer, "%s", data_type_names[type]);
+ if ((name = vsir_data_type_get_name(type, NULL)))
+ vkd3d_string_buffer_printf(&compiler->buffer, "%s", name);
else
vkd3d_string_buffer_printf(&compiler->buffer, "%s<unhandled data type %#x>%s",
compiler->colours.error, type, compiler->colours.reset);
@@ -851,7 +834,7 @@ static void shader_print_register(struct vkd3d_d3d_asm_compiler *compiler, const
&& reg->type != VKD3DSPR_NULL
&& reg->type != VKD3DSPR_DEPTHOUT)
{
- if (offset != ~0u)
+ if (reg->idx_count)
{
bool is_sm_5_1 = vkd3d_shader_ver_ge(&compiler->shader_version, 5, 1);
@@ -879,10 +862,10 @@ static void shader_print_register(struct vkd3d_d3d_asm_compiler *compiler, const
/* For descriptors in sm < 5.1 we move the reg->idx values up one slot
* to normalise with 5.1.
* Here we should ignore it if it's a descriptor in sm < 5.1. */
- if (reg->idx[1].offset != ~0u && (!is_descriptor || is_sm_5_1))
+ if (reg->idx_count > 1 && (!is_descriptor || is_sm_5_1))
shader_print_subscript(compiler, reg->idx[1].offset, reg->idx[1].rel_addr);
- if (reg->idx[2].offset != ~0u)
+ if (reg->idx_count > 2)
shader_print_subscript(compiler, reg->idx[2].offset, reg->idx[2].rel_addr);
}
}
@@ -974,6 +957,22 @@ static void shader_print_reg_type(struct vkd3d_d3d_asm_compiler *compiler,
vkd3d_string_buffer_printf(buffer, ">%s", suffix);
}
+static void shader_print_indexable_temp_data_type(struct vkd3d_d3d_asm_compiler *compiler,
+ const struct vkd3d_shader_indexable_temp *t)
+{
+ struct vkd3d_string_buffer *buffer = &compiler->buffer;
+
+ if (!(compiler->flags & VSIR_ASM_FLAG_DUMP_TYPES))
+ return;
+
+ if (t->component_count > 1)
+ vkd3d_string_buffer_printf(buffer, " <v%u:", t->component_count);
+ else
+ vkd3d_string_buffer_printf(buffer, " <s:");
+ shader_print_data_type(compiler, t->data_type);
+ vkd3d_string_buffer_printf(buffer, ">");
+}
+
static void shader_print_write_mask(struct vkd3d_d3d_asm_compiler *compiler,
const char *prefix, uint32_t mask, const char *suffix)
{
@@ -1528,6 +1527,7 @@ static void shader_dump_instruction(struct vkd3d_d3d_asm_compiler *compiler,
vkd3d_string_buffer_printf(buffer, " %sx%u%s", compiler->colours.reg,
ins->declaration.indexable_temp.register_idx, compiler->colours.reset);
shader_print_subscript(compiler, ins->declaration.indexable_temp.register_size, NULL);
+ shader_print_indexable_temp_data_type(compiler, &ins->declaration.indexable_temp);
shader_print_uint_literal(compiler, ", ", ins->declaration.indexable_temp.component_count, "");
if (ins->declaration.indexable_temp.alignment)
shader_print_uint_literal(compiler, ", align ", ins->declaration.indexable_temp.alignment, "");
diff --git a/libs/vkd3d/libs/vkd3d-shader/d3dbc.c b/libs/vkd3d/libs/vkd3d-shader/d3dbc.c
index 751e5578276..a9195b3454a 100644
--- a/libs/vkd3d/libs/vkd3d-shader/d3dbc.c
+++ b/libs/vkd3d/libs/vkd3d-shader/d3dbc.c
@@ -246,6 +246,7 @@ struct vkd3d_shader_sm1_parser
bool abort;
struct vkd3d_shader_parser p;
+ struct vsir_program *program;
struct
{
@@ -468,7 +469,7 @@ static bool has_relative_address(uint32_t param)
static const struct vkd3d_sm1_opcode_info *shader_sm1_get_opcode_info(
const struct vkd3d_shader_sm1_parser *sm1, enum vkd3d_sm1_opcode opcode)
{
- const struct vkd3d_shader_version *version = &sm1->p.program->shader_version;
+ const struct vkd3d_shader_version *version = &sm1->program->shader_version;
const struct vkd3d_sm1_opcode_info *info;
unsigned int i = 0;
@@ -542,9 +543,9 @@ static enum vkd3d_shader_register_type parse_register_type(
}
if (d3dbc_type == VKD3D_SM1_REG_ADDR)
- return sm1->p.program->shader_version.type == VKD3D_SHADER_TYPE_PIXEL ? VKD3DSPR_TEXTURE : VKD3DSPR_ADDR;
+ return sm1->program->shader_version.type == VKD3D_SHADER_TYPE_PIXEL ? VKD3DSPR_TEXTURE : VKD3DSPR_ADDR;
if (d3dbc_type == VKD3D_SM1_REG_TEXCRDOUT)
- return vkd3d_shader_ver_ge(&sm1->p.program->shader_version, 3, 0) ? VKD3DSPR_OUTPUT : VKD3DSPR_TEXCRDOUT;
+ return vkd3d_shader_ver_ge(&sm1->program->shader_version, 3, 0) ? VKD3DSPR_OUTPUT : VKD3DSPR_TEXCRDOUT;
for (unsigned int i = 0; i < ARRAY_SIZE(register_types); ++i)
{
@@ -660,7 +661,7 @@ static bool add_signature_element(struct vkd3d_shader_sm1_parser *sm1, bool outp
const char *name, unsigned int index, enum vkd3d_shader_sysval_semantic sysval,
unsigned int register_index, bool is_dcl, unsigned int mask)
{
- struct vsir_program *program = sm1->p.program;
+ struct vsir_program *program = sm1->program;
struct shader_signature *signature;
struct signature_element *element;
@@ -702,7 +703,7 @@ static bool add_signature_element(struct vkd3d_shader_sm1_parser *sm1, bool outp
static void add_signature_mask(struct vkd3d_shader_sm1_parser *sm1, bool output,
unsigned int register_index, unsigned int mask)
{
- struct vsir_program *program = sm1->p.program;
+ struct vsir_program *program = sm1->program;
struct shader_signature *signature;
struct signature_element *element;
@@ -749,7 +750,7 @@ static void add_signature_mask(struct vkd3d_shader_sm1_parser *sm1, bool output,
static bool add_signature_element_from_register(struct vkd3d_shader_sm1_parser *sm1,
const struct vkd3d_shader_register *reg, bool is_dcl, unsigned int mask)
{
- const struct vkd3d_shader_version *version = &sm1->p.program->shader_version;
+ const struct vkd3d_shader_version *version = &sm1->program->shader_version;
unsigned int register_index = reg->idx_count > 0 ? reg->idx[0].offset : 0;
switch (reg->type)
@@ -844,7 +845,7 @@ static bool add_signature_element_from_register(struct vkd3d_shader_sm1_parser *
static bool add_signature_element_from_semantic(struct vkd3d_shader_sm1_parser *sm1,
const struct vkd3d_shader_semantic *semantic)
{
- const struct vkd3d_shader_version *version = &sm1->p.program->shader_version;
+ const struct vkd3d_shader_version *version = &sm1->program->shader_version;
const struct vkd3d_shader_register *reg = &semantic->resource.reg.reg;
enum vkd3d_shader_sysval_semantic sysval = VKD3D_SHADER_SV_NONE;
unsigned int mask = semantic->resource.reg.write_mask;
@@ -906,7 +907,7 @@ static void record_constant_register(struct vkd3d_shader_sm1_parser *sm1,
static void shader_sm1_scan_register(struct vkd3d_shader_sm1_parser *sm1,
const struct vkd3d_shader_register *reg, unsigned int mask, bool from_def)
{
- struct vsir_program *program = sm1->p.program;
+ struct vsir_program *program = sm1->program;
uint32_t register_index = reg->idx[0].offset;
switch (reg->type)
@@ -955,7 +956,7 @@ static void shader_sm1_read_param(struct vkd3d_shader_sm1_parser *sm1,
* VS >= 2.0 have relative addressing (with token)
* VS >= 1.0 < 2.0 have relative addressing (without token)
* The version check below should work in general. */
- if (sm1->p.program->shader_version.major < 2)
+ if (sm1->program->shader_version.major < 2)
{
*addr_token = (1u << 31)
| ((VKD3DSPR_ADDR << VKD3D_SM1_REGISTER_TYPE_SHIFT2) & VKD3D_SM1_REGISTER_TYPE_MASK2)
@@ -984,7 +985,7 @@ static void shader_sm1_skip_opcode(const struct vkd3d_shader_sm1_parser *sm1, co
/* Version 2.0+ shaders may contain address tokens, but fortunately they
* have a useful length mask - use it here. Version 1.x shaders contain no
* such tokens. */
- if (sm1->p.program->shader_version.major >= 2)
+ if (sm1->program->shader_version.major >= 2)
{
length = (opcode_token & VKD3D_SM1_INSTRUCTION_LENGTH_MASK) >> VKD3D_SM1_INSTRUCTION_LENGTH_SHIFT;
*ptr += length;
@@ -1019,7 +1020,7 @@ static void shader_sm1_read_src_param(struct vkd3d_shader_sm1_parser *sm1, const
shader_sm1_read_param(sm1, ptr, &token, &addr_token);
if (has_relative_address(token))
{
- if (!(src_rel_addr = vsir_program_get_src_params(sm1->p.program, 1)))
+ if (!(src_rel_addr = vsir_program_get_src_params(sm1->program, 1)))
{
vkd3d_shader_parser_error(&sm1->p, VKD3D_SHADER_ERROR_D3DBC_OUT_OF_MEMORY,
"Out of memory.");
@@ -1040,7 +1041,7 @@ static void shader_sm1_read_dst_param(struct vkd3d_shader_sm1_parser *sm1, const
shader_sm1_read_param(sm1, ptr, &token, &addr_token);
if (has_relative_address(token))
{
- if (!(dst_rel_addr = vsir_program_get_src_params(sm1->p.program, 1)))
+ if (!(dst_rel_addr = vsir_program_get_src_params(sm1->program, 1)))
{
vkd3d_shader_parser_error(&sm1->p, VKD3D_SHADER_ERROR_D3DBC_OUT_OF_MEMORY,
"Out of memory.");
@@ -1052,9 +1053,9 @@ static void shader_sm1_read_dst_param(struct vkd3d_shader_sm1_parser *sm1, const
shader_sm1_parse_dst_param(sm1, token, dst_rel_addr, dst_param);
if (dst_param->reg.type == VKD3DSPR_RASTOUT && dst_param->reg.idx[0].offset == VSIR_RASTOUT_POINT_SIZE)
- sm1->p.program->has_point_size = true;
+ sm1->program->has_point_size = true;
if (dst_param->reg.type == VKD3DSPR_RASTOUT && dst_param->reg.idx[0].offset == VSIR_RASTOUT_FOG)
- sm1->p.program->has_fog = true;
+ sm1->program->has_fog = true;
}
static void shader_sm1_read_semantic(struct vkd3d_shader_sm1_parser *sm1,
@@ -1214,7 +1215,7 @@ static void shader_sm1_read_instruction(struct vkd3d_shader_sm1_parser *sm1, str
{
struct vkd3d_shader_src_param *src_params, *predicate;
const struct vkd3d_sm1_opcode_info *opcode_info;
- struct vsir_program *program = sm1->p.program;
+ struct vsir_program *program = sm1->program;
unsigned int vsir_dst_count, vsir_src_count;
struct vkd3d_shader_dst_param *dst_param;
const uint32_t **ptr = &sm1->ptr;
@@ -1446,7 +1447,8 @@ static enum vkd3d_result shader_sm1_init(struct vkd3d_shader_sm1_parser *sm1, st
code_size != ~(size_t)0 ? token_count / 4u + 4 : 16, VSIR_CF_STRUCTURED, normalisation_level))
return VKD3D_ERROR_OUT_OF_MEMORY;
- vkd3d_shader_parser_init(&sm1->p, program, message_context, compile_info->source_name);
+ vkd3d_shader_parser_init(&sm1->p, message_context, compile_info->source_name);
+ sm1->program = program;
sm1->ptr = sm1->start;
return VKD3D_OK;
@@ -1952,7 +1954,7 @@ static void d3dbc_write_vsir_dcl(struct d3dbc_compiler *d3dbc, const struct vkd3
reg_id = semantic->resource.reg.reg.idx[0].offset;
- if (semantic->resource.reg.reg.type != VKD3DSPR_SAMPLER)
+ if (semantic->resource.reg.reg.type != VKD3DSPR_COMBINED_SAMPLER)
{
vkd3d_shader_error(d3dbc->message_context, &ins->location, VKD3D_SHADER_ERROR_D3DBC_INVALID_REGISTER_TYPE,
"dcl instruction with register type %u.", semantic->resource.reg.reg.type);
diff --git a/libs/vkd3d/libs/vkd3d-shader/dxil.c b/libs/vkd3d/libs/vkd3d-shader/dxil.c
index c448e000cf9..fb2cde4501a 100644
--- a/libs/vkd3d/libs/vkd3d-shader/dxil.c
+++ b/libs/vkd3d/libs/vkd3d-shader/dxil.c
@@ -892,6 +892,8 @@ struct sm6_parser
const uint32_t *ptr, *start, *end;
unsigned int bitpos;
+ struct vsir_program *program;
+
struct dxil_block root_block;
struct dxil_block *current_block;
@@ -2437,7 +2439,7 @@ static struct vkd3d_shader_src_param *instruction_src_params_alloc(struct vkd3d_
{
struct vkd3d_shader_src_param *params;
- if (!(params = vsir_program_get_src_params(sm6->p.program, count)))
+ if (!(params = vsir_program_get_src_params(sm6->program, count)))
{
ERR("Failed to allocate src params.\n");
vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_OUT_OF_MEMORY,
@@ -2454,7 +2456,7 @@ static struct vkd3d_shader_dst_param *instruction_dst_params_alloc(struct vkd3d_
{
struct vkd3d_shader_dst_param *params;
- if (!(params = vsir_program_get_dst_params(sm6->p.program, count)))
+ if (!(params = vsir_program_get_dst_params(sm6->program, count)))
{
ERR("Failed to allocate dst params.\n");
vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_OUT_OF_MEMORY,
@@ -2473,7 +2475,7 @@ static void register_init_with_id(struct vkd3d_shader_register *reg,
reg->idx[0].offset = id;
}
-static enum vsir_data_type vsir_data_type_from_dxil(const struct sm6_type *type)
+static enum vsir_data_type vsir_data_type_from_dxil(const struct sm6_type *type, struct sm6_parser *dxil)
{
if (type->class == TYPE_CLASS_INTEGER)
{
@@ -2490,7 +2492,8 @@ static enum vsir_data_type vsir_data_type_from_dxil(const struct sm6_type *type)
case 64:
return VSIR_DATA_U64;
default:
- FIXME("Unhandled width %u.\n", type->u.width);
+ vkd3d_shader_parser_error(&dxil->p, VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED,
+ "Unhandled integer width %u.", type->u.width);
return VSIR_DATA_U32;
}
}
@@ -2505,12 +2508,14 @@ static enum vsir_data_type vsir_data_type_from_dxil(const struct sm6_type *type)
case 64:
return VSIR_DATA_F64;
default:
- FIXME("Unhandled width %u.\n", type->u.width);
+ vkd3d_shader_parser_error(&dxil->p, VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED,
+ "Unhandled floating-point width %u.", type->u.width);
return VSIR_DATA_F32;
}
}
- FIXME("Unhandled type %u.\n", type->class);
+ vkd3d_shader_parser_error(&dxil->p, VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED,
+ "Unhandled type %#x.", type->class);
return VSIR_DATA_U32;
}
@@ -2597,7 +2602,7 @@ static void sm6_register_from_value(struct vkd3d_shader_register *reg, const str
enum vsir_data_type data_type;
scalar_type = sm6_type_get_scalar_type(value->type, 0);
- data_type = vsir_data_type_from_dxil(scalar_type);
+ data_type = vsir_data_type_from_dxil(scalar_type, sm6);
switch (value->value_type)
{
@@ -2756,7 +2761,7 @@ static void register_index_address_init(struct vkd3d_shader_register_index *idx,
}
else
{
- struct vkd3d_shader_src_param *rel_addr = vsir_program_get_src_params(sm6->p.program, 1);
+ struct vkd3d_shader_src_param *rel_addr = vsir_program_get_src_params(sm6->program, 1);
if (rel_addr)
src_param_init_from_value(rel_addr, address, sm6);
idx->offset = 0;
@@ -3224,7 +3229,7 @@ static enum vkd3d_result value_allocate_constant_array(struct sm6_value *dst, co
"Out of memory allocating an immediate constant buffer of count %u.", count);
return VKD3D_ERROR_OUT_OF_MEMORY;
}
- if (!shader_instruction_array_add_icb(&sm6->p.program->instructions, icb))
+ if (!shader_instruction_array_add_icb(&sm6->program->instructions, icb))
{
ERR("Failed to store icb object.\n");
vkd3d_free(icb);
@@ -3237,7 +3242,7 @@ static enum vkd3d_result value_allocate_constant_array(struct sm6_value *dst, co
dst->u.data = icb;
icb->register_idx = sm6->icb_count++;
- icb->data_type = vsir_data_type_from_dxil(elem_type);
+ icb->data_type = vsir_data_type_from_dxil(elem_type, sm6);
icb->element_count = type->u.array.count;
icb->component_count = 1;
icb->is_null = !operands;
@@ -3653,7 +3658,7 @@ static bool bitcode_parse_alignment(uint64_t encoded_alignment, unsigned int *al
static struct vkd3d_shader_instruction *sm6_parser_require_space(struct sm6_parser *sm6, size_t extra)
{
- struct vkd3d_shader_instruction_array *instructions = &sm6->p.program->instructions;
+ struct vkd3d_shader_instruction_array *instructions = &sm6->program->instructions;
if (!shader_instruction_array_reserve(instructions, instructions->count + extra))
{
@@ -3663,14 +3668,15 @@ static struct vkd3d_shader_instruction *sm6_parser_require_space(struct sm6_pars
return &instructions->elements[instructions->count];
}
-/* Space should be reserved before calling this. It is intended to require no checking of the returned pointer. */
static struct vkd3d_shader_instruction *sm6_parser_add_instruction(struct sm6_parser *sm6,
- enum vkd3d_shader_opcode handler_idx)
+ enum vkd3d_shader_opcode op)
{
- struct vkd3d_shader_instruction *ins = sm6_parser_require_space(sm6, 1);
- VKD3D_ASSERT(ins);
- vsir_instruction_init(ins, &sm6->p.location, handler_idx);
- ++sm6->p.program->instructions.count;
+ struct vkd3d_shader_instruction *ins;
+
+ if (!(ins = vsir_program_append(sm6->program)))
+ return NULL;
+ vsir_instruction_init(ins, &sm6->p.location, op);
+
return ins;
}
@@ -3690,7 +3696,15 @@ static void sm6_parser_declare_indexable_temp(struct sm6_parser *sm6, const stru
unsigned int count, unsigned int alignment, bool has_function_scope, unsigned int init,
struct vkd3d_shader_instruction *ins, struct sm6_value *dst)
{
- enum vsir_data_type data_type = vsir_data_type_from_dxil(elem_type);
+ enum vsir_data_type data_type = vsir_data_type_from_dxil(elem_type, sm6);
+
+ if (!(sm6->program->global_flags & VKD3DSGF_FORCE_NATIVE_LOW_PRECISION))
+ {
+ if (data_type == VSIR_DATA_F16)
+ data_type = VSIR_DATA_F32;
+ else if (data_type == VSIR_DATA_U16)
+ data_type = VSIR_DATA_U32;
+ }
if (ins)
vsir_instruction_init(ins, &sm6->p.location, VSIR_OP_DCL_INDEXABLE_TEMP);
@@ -3969,7 +3983,7 @@ static bool resolve_forward_zero_initialiser(size_t index, struct sm6_parser *sm
static enum vkd3d_result sm6_parser_globals_init(struct sm6_parser *sm6)
{
- struct vsir_program_iterator it = vsir_program_iterator(&sm6->p.program->instructions);
+ struct vsir_program_iterator it = vsir_program_iterator(&sm6->program->instructions);
size_t i, count, base_value_idx = sm6->value_count;
const struct dxil_block *block = &sm6->root_block;
struct vkd3d_shader_instruction *ins;
@@ -4009,8 +4023,7 @@ static enum vkd3d_result sm6_parser_globals_init(struct sm6_parser *sm6)
return VKD3D_ERROR_INVALID_SHADER;
if ((version = record->operands[0]) != 1)
{
- FIXME("Unsupported format version %#"PRIx64".\n", version);
- vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED_BITCODE_FORMAT,
+ vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED,
"Bitcode format version %#"PRIx64" is unsupported.", version);
return VKD3D_ERROR_INVALID_SHADER;
}
@@ -4125,7 +4138,7 @@ static enum vkd3d_shader_register_type register_type_from_dxil_semantic_kind(
static void sm6_parser_init_signature(struct sm6_parser *sm6, const struct shader_signature *s,
bool is_input, enum vkd3d_shader_register_type reg_type, struct vkd3d_shader_dst_param *params)
{
- enum vkd3d_shader_type shader_type = sm6->p.program->shader_version.type;
+ enum vkd3d_shader_type shader_type = sm6->program->shader_version.type;
enum vkd3d_shader_register_type io_reg_type;
bool is_patch_constant, is_control_point;
struct vkd3d_shader_dst_param *param;
@@ -4175,7 +4188,7 @@ static void sm6_parser_init_signature(struct sm6_parser *sm6, const struct shade
if (is_control_point)
{
if (reg_type == VKD3DSPR_OUTPUT)
- param->reg.idx[count].rel_addr = vsir_program_create_outpointid_param(sm6->p.program);
+ param->reg.idx[count].rel_addr = vsir_program_create_outpointid_param(sm6->program);
param->reg.idx[count++].offset = 0;
}
@@ -4190,7 +4203,7 @@ static void sm6_parser_init_signature(struct sm6_parser *sm6, const struct shade
static int sm6_parser_init_output_signature(struct sm6_parser *sm6, const struct shader_signature *output_signature)
{
- if (!(sm6->output_params = vsir_program_get_dst_params(sm6->p.program, output_signature->element_count)))
+ if (!(sm6->output_params = vsir_program_get_dst_params(sm6->program, output_signature->element_count)))
{
vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_OUT_OF_MEMORY,
"Failed to allocate output parameters.");
@@ -4204,7 +4217,7 @@ static int sm6_parser_init_output_signature(struct sm6_parser *sm6, const struct
static int sm6_parser_init_input_signature(struct sm6_parser *sm6, const struct shader_signature *input_signature)
{
- if (!(sm6->input_params = vsir_program_get_dst_params(sm6->p.program, input_signature->element_count)))
+ if (!(sm6->input_params = vsir_program_get_dst_params(sm6->program, input_signature->element_count)))
{
vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_OUT_OF_MEMORY,
"Failed to allocate input parameters.");
@@ -4219,9 +4232,9 @@ static int sm6_parser_init_input_signature(struct sm6_parser *sm6, const struct
static int sm6_parser_init_patch_constant_signature(struct sm6_parser *sm6,
const struct shader_signature *patch_constant_signature)
{
- bool is_input = sm6->p.program->shader_version.type == VKD3D_SHADER_TYPE_DOMAIN;
+ bool is_input = sm6->program->shader_version.type == VKD3D_SHADER_TYPE_DOMAIN;
- if (!(sm6->patch_constant_params = vsir_program_get_dst_params(sm6->p.program,
+ if (!(sm6->patch_constant_params = vsir_program_get_dst_params(sm6->program,
patch_constant_signature->element_count)))
{
vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_OUT_OF_MEMORY,
@@ -5180,7 +5193,7 @@ static void sm6_parser_emit_dx_cbuffer_load(struct sm6_parser *sm6, enum dx_intr
type = sm6_type_get_scalar_type(dst->type, 0);
VKD3D_ASSERT(type);
- src_param->reg.data_type = vsir_data_type_from_dxil(type);
+ src_param->reg.data_type = vsir_data_type_from_dxil(type, sm6);
if (data_type_is_64_bit(src_param->reg.data_type))
src_param->swizzle = vsir_swizzle_64_from_32(src_param->swizzle);
else
@@ -5407,7 +5420,7 @@ static void sm6_parser_emit_dx_eval_attrib(struct sm6_parser *sm6, enum dx_intri
row_index = sm6_value_get_constant_uint(operands[0], sm6);
column_index = sm6_value_get_constant_uint(operands[2], sm6);
- signature = &sm6->p.program->input_signature;
+ signature = &sm6->program->input_signature;
if (row_index >= signature->element_count)
{
WARN("Invalid row index %u.\n", row_index);
@@ -5638,7 +5651,7 @@ static void sm6_parser_emit_dx_load_input(struct sm6_parser *sm6, enum dx_intrin
bool is_control_point = op == DX_LOAD_OUTPUT_CONTROL_POINT;
bool is_patch_constant = op == DX_LOAD_PATCH_CONSTANT;
struct vkd3d_shader_instruction *ins = state->ins;
- struct vsir_program *program = sm6->p.program;
+ struct vsir_program *program = sm6->program;
unsigned int count, row_index, column_index;
const struct vkd3d_shader_dst_param *params;
struct vkd3d_shader_src_param *src_param;
@@ -6148,7 +6161,7 @@ static void sm6_parser_emit_dx_sample(struct sm6_parser *sm6, enum dx_intrinsic_
static void sm6_parser_emit_dx_sample_index(struct sm6_parser *sm6, enum dx_intrinsic_opcode op,
const struct sm6_value **operands, struct function_emission_state *state)
{
- const struct shader_signature *signature = &sm6->p.program->input_signature;
+ const struct shader_signature *signature = &sm6->program->input_signature;
struct vkd3d_shader_instruction *ins = state->ins;
struct vkd3d_shader_src_param *src_param;
unsigned int element_idx;
@@ -6207,7 +6220,7 @@ static void sm6_parser_emit_dx_store_output(struct sm6_parser *sm6, enum dx_intr
{
bool is_patch_constant = op == DX_STORE_PATCH_CONSTANT;
struct vkd3d_shader_instruction *ins = state->ins;
- struct vsir_program *program = sm6->p.program;
+ struct vsir_program *program = sm6->program;
struct vkd3d_shader_src_param *src_param;
struct vkd3d_shader_dst_param *dst_param;
const struct shader_signature *signature;
@@ -8206,7 +8219,7 @@ static enum vkd3d_result sm6_function_resolve_phi_incomings(const struct sm6_fun
static enum vkd3d_result sm6_parser_function_init(struct sm6_parser *sm6, const struct dxil_block *block,
struct sm6_function *function)
{
- struct vsir_program *program = sm6->p.program;
+ struct vsir_program *program = sm6->program;
struct vkd3d_shader_instruction *ins;
size_t i, block_idx, block_count;
const struct dxil_record *record;
@@ -8586,8 +8599,9 @@ static void sm6_parser_emit_label(struct sm6_parser *sm6, unsigned int label_id)
static enum vkd3d_result sm6_function_emit_blocks(const struct sm6_function *function, struct sm6_parser *sm6)
{
- struct vsir_program *program = sm6->p.program;
- unsigned int i;
+ struct vsir_program *program = sm6->program;
+ struct vkd3d_shader_instruction *ins;
+ unsigned int i, j;
program->block_count = function->block_count;
@@ -8605,10 +8619,11 @@ static enum vkd3d_result sm6_function_emit_blocks(const struct sm6_function *fun
sm6_parser_emit_label(sm6, block->id);
sm6_block_emit_phi(block, sm6);
- memcpy(&program->instructions.elements[program->instructions.count], block->instructions,
- block->instruction_count * sizeof(*block->instructions));
- program->instructions.count += block->instruction_count;
-
+ for (j = 0; j < block->instruction_count; ++j)
+ {
+ ins = vsir_program_append(program);
+ *ins = block->instructions[j];
+ }
sm6_block_emit_terminator(block, sm6);
}
@@ -9510,8 +9525,8 @@ static enum vkd3d_result sm6_parser_descriptor_type_init(struct sm6_parser *sm6,
struct vkd3d_shader_instruction *ins;
const struct sm6_metadata_node *node;
const struct sm6_metadata_value *m;
+ enum vkd3d_result ret = VKD3D_OK;
struct sm6_descriptor_info *d;
- enum vkd3d_result ret;
unsigned int i;
for (i = 0; i < descriptor_node->operand_count; ++i)
@@ -9560,9 +9575,10 @@ static enum vkd3d_result sm6_parser_descriptor_type_init(struct sm6_parser *sm6,
return VKD3D_ERROR_INVALID_SHADER;
}
- if (!(ins = sm6_parser_require_space(sm6, 1)))
+ if (!(ins = sm6_parser_add_instruction(sm6, VSIR_OP_NOP)))
{
- ERR("Failed to allocate instruction.\n");
+ vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_OUT_OF_MEMORY,
+ "Out of memory emitting shader instructions.");
return VKD3D_ERROR_OUT_OF_MEMORY;
}
@@ -9570,32 +9586,34 @@ static enum vkd3d_result sm6_parser_descriptor_type_init(struct sm6_parser *sm6,
{
case VKD3D_SHADER_DESCRIPTOR_TYPE_CBV:
if ((ret = sm6_parser_resources_load_cbv(sm6, node, d, ins)) < 0)
- return ret;
+ goto done;
break;
case VKD3D_SHADER_DESCRIPTOR_TYPE_SRV:
if ((ret = sm6_parser_resources_load_srv(sm6, node, d, ins)) < 0)
- return ret;
+ goto done;
break;
case VKD3D_SHADER_DESCRIPTOR_TYPE_UAV:
if ((ret = sm6_parser_resources_load_uav(sm6, node, d, ins)) < 0)
- return ret;
+ goto done;
break;
case VKD3D_SHADER_DESCRIPTOR_TYPE_SAMPLER:
if ((ret = sm6_parser_resources_load_sampler(sm6, node, d, ins)) < 0)
- return ret;
+ goto done;
break;
default:
- FIXME("Unsupported descriptor type %u.\n", type);
vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_INVALID_RESOURCES,
- "Resource descriptor type %u is unsupported.", type);
- return VKD3D_ERROR_INVALID_SHADER;
+ "Resource descriptor type %#x is unsupported.", type);
+ ret = VKD3D_ERROR_INVALID_SHADER;
+ goto done;
}
++sm6->descriptor_count;
- ++sm6->p.program->instructions.count;
}
- return VKD3D_OK;
+done:
+ if (ret < 0)
+ vsir_instruction_init(ins, &ins->location, VSIR_OP_NOP);
+ return ret;
}
static enum vkd3d_result sm6_parser_resources_init(struct sm6_parser *sm6)
@@ -9711,7 +9729,7 @@ static enum vkd3d_result sm6_parser_read_signature(struct sm6_parser *sm6, const
{
unsigned int i, j, column_count, operand_count, index;
const struct sm6_metadata_node *node, *element_node;
- struct vsir_program *program = sm6->p.program;
+ struct vsir_program *program = sm6->program;
struct signature_element *elements, *e;
unsigned int values[10];
bool native_16bit;
@@ -9930,7 +9948,7 @@ invalid:
static enum vkd3d_result sm6_parser_signatures_init(struct sm6_parser *sm6, const struct sm6_metadata_value *m,
enum vkd3d_tessellator_domain tessellator_domain)
{
- struct vsir_program *program = sm6->p.program;
+ struct vsir_program *program = sm6->program;
enum vkd3d_result ret;
if (!sm6_metadata_value_is_node(m))
@@ -9985,12 +10003,12 @@ static void sm6_parser_emit_global_flags(struct sm6_parser *sm6, const struct sm
ins = sm6_parser_add_instruction(sm6, VSIR_OP_DCL_GLOBAL_FLAGS);
ins->declaration.global_flags = global_flags;
- sm6->p.program->global_flags = global_flags;
+ sm6->program->global_flags = global_flags;
}
static enum vkd3d_result sm6_parser_emit_thread_group(struct sm6_parser *sm6, const struct sm6_metadata_value *m)
{
- struct vkd3d_shader_version *version = &sm6->p.program->shader_version;
+ struct vkd3d_shader_version *version = &sm6->program->shader_version;
const struct sm6_metadata_node *node;
struct vkd3d_shader_instruction *ins;
unsigned int group_sizes[3];
@@ -10044,7 +10062,7 @@ static enum vkd3d_result sm6_parser_emit_thread_group(struct sm6_parser *sm6, co
ins->declaration.thread_group_size.x = group_sizes[0];
ins->declaration.thread_group_size.y = group_sizes[1];
ins->declaration.thread_group_size.z = group_sizes[2];
- sm6->p.program->thread_group_size = ins->declaration.thread_group_size;
+ sm6->program->thread_group_size = ins->declaration.thread_group_size;
return VKD3D_OK;
}
@@ -10082,7 +10100,7 @@ static void sm6_parser_emit_dcl_tessellator_domain(struct sm6_parser *sm6,
ins = sm6_parser_add_instruction(sm6, VSIR_OP_DCL_TESSELLATOR_DOMAIN);
ins->declaration.tessellator_domain = tessellator_domain;
- sm6->p.program->tess_domain = tessellator_domain;
+ sm6->program->tess_domain = tessellator_domain;
}
static void sm6_parser_validate_control_point_count(struct sm6_parser *sm6,
@@ -10111,7 +10129,7 @@ static void sm6_parser_emit_dcl_tessellator_partitioning(struct sm6_parser *sm6,
ins = sm6_parser_add_instruction(sm6, VSIR_OP_DCL_TESSELLATOR_PARTITIONING);
ins->declaration.tessellator_partitioning = tessellator_partitioning;
- sm6->p.program->tess_partitioning = tessellator_partitioning;
+ sm6->program->tess_partitioning = tessellator_partitioning;
}
static void sm6_parser_emit_dcl_tessellator_output_primitive(struct sm6_parser *sm6,
@@ -10129,7 +10147,7 @@ static void sm6_parser_emit_dcl_tessellator_output_primitive(struct sm6_parser *
ins = sm6_parser_add_instruction(sm6, VSIR_OP_DCL_TESSELLATOR_OUTPUT_PRIMITIVE);
ins->declaration.tessellator_output_primitive = primitive;
- sm6->p.program->tess_output_primitive = primitive;
+ sm6->program->tess_output_primitive = primitive;
}
static void sm6_parser_emit_dcl_max_tessellation_factor(struct sm6_parser *sm6, struct sm6_metadata_value *m)
@@ -10241,8 +10259,8 @@ static void sm6_parser_gs_properties_init(struct sm6_parser *sm6, const struct s
}
sm6_parser_emit_dcl_primitive_topology(sm6, VSIR_OP_DCL_INPUT_PRIMITIVE, input_primitive, patch_vertex_count);
- sm6->p.program->input_primitive = input_primitive;
- sm6->p.program->input_control_point_count = input_control_point_count;
+ sm6->program->input_primitive = input_primitive;
+ sm6->program->input_control_point_count = input_control_point_count;
i = operands[1];
/* Max total scalar count sets an upper limit. We would need to scan outputs to be more precise. */
@@ -10253,7 +10271,7 @@ static void sm6_parser_gs_properties_init(struct sm6_parser *sm6, const struct s
"Geometry shader output vertex count %u is invalid.", i);
}
sm6_parser_emit_dcl_count(sm6, VSIR_OP_DCL_VERTICES_OUT, i);
- sm6->p.program->vertices_out_count = i;
+ sm6->program->vertices_out_count = i;
if (operands[2] > 1)
{
@@ -10271,7 +10289,7 @@ static void sm6_parser_gs_properties_init(struct sm6_parser *sm6, const struct s
output_primitive = VKD3D_PT_TRIANGLELIST;
}
sm6_parser_emit_dcl_primitive_topology(sm6, VSIR_OP_DCL_OUTPUT_TOPOLOGY, output_primitive, 0);
- sm6->p.program->output_topology = output_primitive;
+ sm6->program->output_topology = output_primitive;
i = operands[4];
if (!i || i > MAX_GS_INSTANCE_COUNT)
@@ -10326,7 +10344,7 @@ static enum vkd3d_tessellator_domain sm6_parser_ds_properties_init(struct sm6_pa
sm6_parser_emit_dcl_tessellator_domain(sm6, operands[0]);
sm6_parser_validate_control_point_count(sm6, operands[1], true, "Domain shader input");
- sm6->p.program->input_control_point_count = operands[1];
+ sm6->program->input_control_point_count = operands[1];
return operands[0];
}
@@ -10334,7 +10352,7 @@ static enum vkd3d_tessellator_domain sm6_parser_ds_properties_init(struct sm6_pa
static enum vkd3d_tessellator_domain sm6_parser_hs_properties_init(struct sm6_parser *sm6,
const struct sm6_metadata_value *m)
{
- struct vsir_program *program = sm6->p.program;
+ struct vsir_program *program = sm6->program;
const struct sm6_metadata_node *node;
unsigned int operands[6] = {0};
unsigned int i;
@@ -10727,9 +10745,10 @@ static enum vkd3d_result sm6_parser_init(struct sm6_parser *sm6, struct vsir_pro
if (!vsir_program_init(program, compile_info, &version,
(count + (count >> 2)) / 2u + 10, VSIR_CF_BLOCKS, VSIR_NORMALISED_SM6))
return VKD3D_ERROR_OUT_OF_MEMORY;
- vkd3d_shader_parser_init(&sm6->p, program, message_context, compile_info->source_name);
+ vkd3d_shader_parser_init(&sm6->p, message_context, compile_info->source_name);
sm6->ptr = &sm6->start[1];
sm6->bitpos = 2;
+ sm6->program = program;
switch (program->shader_version.type)
{
diff --git a/libs/vkd3d/libs/vkd3d-shader/fx.c b/libs/vkd3d/libs/vkd3d-shader/fx.c
index 676c501bb08..a14346a45d2 100644
--- a/libs/vkd3d/libs/vkd3d-shader/fx.c
+++ b/libs/vkd3d/libs/vkd3d-shader/fx.c
@@ -4205,7 +4205,7 @@ static void fx_parse_shader_blob(struct fx_parser *parser, enum vkd3d_shader_sou
static const struct vkd3d_shader_compile_option options[] =
{
- {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_1_17},
+ {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_CURRENT},
};
info.type = VKD3D_SHADER_STRUCTURE_TYPE_COMPILE_INFO;
diff --git a/libs/vkd3d/libs/vkd3d-shader/glsl.c b/libs/vkd3d/libs/vkd3d-shader/glsl.c
index dfe0a40ddf0..b2679beff9f 100644
--- a/libs/vkd3d/libs/vkd3d-shader/glsl.c
+++ b/libs/vkd3d/libs/vkd3d-shader/glsl.c
@@ -288,6 +288,14 @@ static void shader_glsl_print_register_name(struct vkd3d_string_buffer *buffer,
shader_glsl_print_subscript(buffer, gen, reg->idx[1].rel_addr, reg->idx[1].offset);
break;
+ case VKD3DSPR_SAMPLEMASK:
+ if (gen->program->shader_version.type != VKD3D_SHADER_TYPE_PIXEL)
+ vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_INTERNAL,
+ "Internal compiler error: Unhandled sample coverage mask in shader type #%x.",
+ gen->program->shader_version.type);
+ vkd3d_string_buffer_printf(buffer, "o_mask");
+ break;
+
default:
vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_INTERNAL,
"Internal compiler error: Unhandled register type %#x.", reg->type);
@@ -792,7 +800,7 @@ static void shader_glsl_print_texel_offset(struct vkd3d_string_buffer *buffer, s
static void shader_glsl_ld(struct vkd3d_glsl_generator *gen, const struct vkd3d_shader_instruction *ins)
{
- unsigned int resource_id, resource_idx, resource_space, sample_count;
+ unsigned int coord_size, resource_id, resource_idx, resource_space, sample_count;
const struct glsl_resource_type_info *resource_type_info;
const struct vkd3d_shader_descriptor_info1 *d;
enum vkd3d_shader_resource_type resource_type;
@@ -800,11 +808,9 @@ static void shader_glsl_ld(struct vkd3d_glsl_generator *gen, const struct vkd3d_
enum vsir_data_type data_type;
struct glsl_src coord;
struct glsl_dst dst;
- uint32_t coord_mask;
+ bool array, offset;
- if (vkd3d_shader_instruction_has_texel_offset(ins))
- vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_INTERNAL,
- "Internal compiler error: Unhandled texel fetch offset.");
+ offset = vkd3d_shader_instruction_has_texel_offset(ins);
if (ins->src[1].reg.idx[0].rel_addr || ins->src[1].reg.idx[1].rel_addr)
vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_UNSUPPORTED,
@@ -831,20 +837,22 @@ static void shader_glsl_ld(struct vkd3d_glsl_generator *gen, const struct vkd3d_
if ((resource_type_info = shader_glsl_get_resource_type_info(resource_type)))
{
- coord_mask = vkd3d_write_mask_from_component_count(resource_type_info->coord_size);
+ coord_size = resource_type_info->coord_size;
+ array = resource_type_info->array;
}
else
{
vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_INTERNAL,
"Internal compiler error: Unhandled resource type %#x.", resource_type);
- coord_mask = vkd3d_write_mask_from_component_count(2);
+ coord_size = 2;
+ array = false;
}
glsl_dst_init(&dst, gen, ins, &ins->dst[0]);
- glsl_src_init(&coord, gen, &ins->src[0], coord_mask);
+ glsl_src_init(&coord, gen, &ins->src[0], vkd3d_write_mask_from_component_count(coord_size));
fetch = vkd3d_string_buffer_get(&gen->string_buffers);
- vkd3d_string_buffer_printf(fetch, "texelFetch(");
+ vkd3d_string_buffer_printf(fetch, "texelFetch%s(", offset ? "Offset" : "");
shader_glsl_print_combined_sampler_name(fetch, gen, resource_idx,
resource_space, VKD3D_SHADER_DUMMY_SAMPLER_INDEX, 0);
vkd3d_string_buffer_printf(fetch, ", %s", coord.str->buffer);
@@ -860,6 +868,11 @@ static void shader_glsl_ld(struct vkd3d_glsl_generator *gen, const struct vkd3d_
else
shader_glsl_print_src(fetch, gen, &ins->src[2], VKD3DSP_WRITEMASK_0, ins->src[2].reg.data_type);
}
+ if (offset)
+ {
+ vkd3d_string_buffer_printf(fetch, ", ");
+ shader_glsl_print_texel_offset(fetch, gen, coord_size - array, &ins->texel_offset);
+ }
vkd3d_string_buffer_printf(fetch, ")");
shader_glsl_print_swizzle(fetch, ins->src[1].swizzle, ins->dst[0].write_mask);
@@ -1281,6 +1294,13 @@ static void shader_glsl_print_sysval_name(struct vkd3d_string_buffer *buffer, st
vkd3d_string_buffer_printf(buffer, "intBitsToFloat(ivec4(gl_VertexID, 0, 0, 0))");
break;
+ case VKD3D_SHADER_SV_INSTANCE_ID:
+ if (version->type != VKD3D_SHADER_TYPE_VERTEX)
+ vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_INTERNAL,
+ "Internal compiler error: Unhandled SV_INSTANCE_ID in shader type #%x.", version->type);
+ vkd3d_string_buffer_printf(buffer, "intBitsToFloat(ivec4(gl_InstanceID, 0, 0, 0))");
+ break;
+
case VKD3D_SHADER_SV_IS_FRONT_FACE:
if (version->type != VKD3D_SHADER_TYPE_PIXEL)
vkd3d_glsl_compiler_error(gen, VKD3D_SHADER_ERROR_GLSL_INTERNAL,
@@ -1429,6 +1449,12 @@ static void shader_glsl_shader_epilogue(struct vkd3d_glsl_generator *gen)
shader_glsl_print_write_mask(buffer, e->mask);
vkd3d_string_buffer_printf(buffer, ";\n");
}
+
+ if (bitmap_is_set(gen->program->io_dcls, VKD3DSPR_SAMPLEMASK))
+ {
+ shader_glsl_print_indent(buffer, gen->indent);
+ vkd3d_string_buffer_printf(gen->buffer, "gl_SampleMask[0] = floatBitsToInt(o_mask);\n");
+ }
}
static void shader_glsl_ret(struct vkd3d_glsl_generator *gen, const struct vkd3d_shader_instruction *ins)
@@ -1475,6 +1501,9 @@ static void vkd3d_glsl_handle_instruction(struct vkd3d_glsl_generator *gen,
case VSIR_OP_CONTINUE:
shader_glsl_continue(gen);
break;
+ case VSIR_OP_COS:
+ shader_glsl_intrinsic(gen, ins, "cos");
+ break;
case VSIR_OP_DCL_INDEXABLE_TEMP:
shader_glsl_dcl_indexable_temp(gen, ins);
break;
@@ -1495,6 +1524,12 @@ static void vkd3d_glsl_handle_instruction(struct vkd3d_glsl_generator *gen,
case VSIR_OP_DP4:
shader_glsl_dot(gen, ins, VKD3DSP_WRITEMASK_ALL);
break;
+ case VSIR_OP_DSX:
+ shader_glsl_intrinsic(gen, ins, "dFdx");
+ break;
+ case VSIR_OP_DSY:
+ shader_glsl_intrinsic(gen, ins, "dFdy");
+ break;
case VSIR_OP_ELSE:
shader_glsl_else(gen, ins);
break;
@@ -1531,6 +1566,7 @@ static void vkd3d_glsl_handle_instruction(struct vkd3d_glsl_generator *gen,
break;
case VSIR_OP_GEO:
case VSIR_OP_IGE:
+ case VSIR_OP_UGE:
shader_glsl_relop(gen, ins, ">=", "greaterThanEqual");
break;
case VSIR_OP_IF:
@@ -1620,6 +1656,9 @@ static void vkd3d_glsl_handle_instruction(struct vkd3d_glsl_generator *gen,
case VSIR_OP_RSQ:
shader_glsl_intrinsic(gen, ins, "inversesqrt");
break;
+ case VSIR_OP_SIN:
+ shader_glsl_intrinsic(gen, ins, "sin");
+ break;
case VSIR_OP_SQRT:
shader_glsl_intrinsic(gen, ins, "sqrt");
break;
@@ -1629,6 +1668,12 @@ static void vkd3d_glsl_handle_instruction(struct vkd3d_glsl_generator *gen,
case VSIR_OP_SWITCH:
shader_glsl_switch(gen, ins);
break;
+ case VSIR_OP_UDIV_SIMPLE:
+ shader_glsl_binop(gen, ins, "/");
+ break;
+ case VSIR_OP_UREM:
+ shader_glsl_binop(gen, ins, "%");
+ break;
case VSIR_OP_XOR:
shader_glsl_binop(gen, ins, "^");
break;
@@ -2318,6 +2363,8 @@ static void shader_glsl_generate_declarations(struct vkd3d_glsl_generator *gen)
vkd3d_string_buffer_printf(buffer, "vec4 %s_in[%u];\n", gen->prefix, gen->limits.input_count);
if (gen->limits.output_count)
vkd3d_string_buffer_printf(buffer, "vec4 %s_out[%u];\n", gen->prefix, gen->limits.output_count);
+ if (bitmap_is_set(gen->program->io_dcls, VKD3DSPR_SAMPLEMASK))
+ vkd3d_string_buffer_printf(gen->buffer, "float o_mask;\n");
if (program->temp_count)
vkd3d_string_buffer_printf(buffer, "vec4 r[%u];\n", program->temp_count);
vkd3d_string_buffer_printf(buffer, "\n");
@@ -2328,7 +2375,6 @@ static int vkd3d_glsl_generator_generate(struct vkd3d_glsl_generator *gen, struc
struct vkd3d_string_buffer *buffer = gen->buffer;
struct vkd3d_shader_instruction *ins;
struct vsir_program_iterator it;
- void *code;
MESSAGE("Generating a GLSL shader. This is unsupported; you get to keep all the pieces if it breaks.\n");
@@ -2357,13 +2403,7 @@ static int vkd3d_glsl_generator_generate(struct vkd3d_glsl_generator *gen, struc
if (gen->failed)
return VKD3D_ERROR_INVALID_SHADER;
- if ((code = vkd3d_malloc(buffer->buffer_size)))
- {
- memcpy(code, buffer->buffer, buffer->content_size);
- out->size = buffer->content_size;
- out->code = code;
- }
- else return VKD3D_ERROR_OUT_OF_MEMORY;
+ vkd3d_shader_code_from_string_buffer(out, buffer);
return VKD3D_OK;
}
diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl.c b/libs/vkd3d/libs/vkd3d-shader/hlsl.c
index 62335086e20..d8eb18e39c7 100644
--- a/libs/vkd3d/libs/vkd3d-shader/hlsl.c
+++ b/libs/vkd3d/libs/vkd3d-shader/hlsl.c
@@ -1809,6 +1809,76 @@ struct hlsl_ir_node *hlsl_new_null_constant(struct hlsl_ctx *ctx, const struct v
return hlsl_new_constant(ctx, ctx->builtin_types.null, &value, loc);
}
+bool hlsl_constant_is_zero(struct hlsl_ir_constant *c)
+{
+ struct hlsl_type *data_type = c->node.data_type;
+ unsigned int k;
+
+ for (k = 0; k < data_type->e.numeric.dimx; ++k)
+ {
+ switch (data_type->e.numeric.type)
+ {
+ case HLSL_TYPE_FLOAT:
+ case HLSL_TYPE_HALF:
+ if (c->value.u[k].f != 0.0f)
+ return false;
+ break;
+
+ case HLSL_TYPE_DOUBLE:
+ if (c->value.u[k].d != 0.0)
+ return false;
+ break;
+
+ case HLSL_TYPE_UINT:
+ case HLSL_TYPE_INT:
+ case HLSL_TYPE_BOOL:
+ case HLSL_TYPE_MIN16UINT:
+ if (c->value.u[k].u != 0)
+ return false;
+ break;
+ }
+ }
+
+ return true;
+}
+
+bool hlsl_constant_is_one(struct hlsl_ir_constant *c)
+{
+ struct hlsl_type *data_type = c->node.data_type;
+ unsigned int k;
+
+ for (k = 0; k < data_type->e.numeric.dimx; ++k)
+ {
+ switch (data_type->e.numeric.type)
+ {
+ case HLSL_TYPE_FLOAT:
+ case HLSL_TYPE_HALF:
+ if (c->value.u[k].f != 1.0f)
+ return false;
+ break;
+
+ case HLSL_TYPE_DOUBLE:
+ if (c->value.u[k].d != 1.0)
+ return false;
+ break;
+
+ case HLSL_TYPE_UINT:
+ case HLSL_TYPE_INT:
+ case HLSL_TYPE_MIN16UINT:
+ if (c->value.u[k].u != 1)
+ return false;
+ break;
+
+ case HLSL_TYPE_BOOL:
+ if (c->value.u[k].u != ~0)
+ return false;
+ break;
+ }
+ }
+
+ return true;
+}
+
static struct hlsl_ir_node *hlsl_new_expr(struct hlsl_ctx *ctx, enum hlsl_ir_expr_op op,
struct hlsl_ir_node *operands[HLSL_MAX_OPERANDS],
struct hlsl_type *data_type, const struct vkd3d_shader_location *loc)
diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl.h b/libs/vkd3d/libs/vkd3d-shader/hlsl.h
index d67f820fe8b..a3e8ccc1e2a 100644
--- a/libs/vkd3d/libs/vkd3d-shader/hlsl.h
+++ b/libs/vkd3d/libs/vkd3d-shader/hlsl.h
@@ -233,6 +233,9 @@ struct hlsl_type
/* Offset where the type's description starts in the output bytecode, in bytes. */
size_t bytecode_offset;
+ /* Offset where the type's packed description starts in the output bytecode, in bytes. */
+ size_t packed_bytecode_offset;
+
bool is_typedef;
uint32_t is_minimum_precision : 1;
@@ -1184,8 +1187,8 @@ struct hlsl_ctx
} constant_defs;
/* 'c' registers where the constants expected by SM2 sincos are stored. */
struct hlsl_reg d3dsincosconst1, d3dsincosconst2;
- /* Number of allocated SSA IDs, used in translation to vsir. */
- unsigned int ssa_count;
+ /* Number of allocated registers, used in translation to vsir. */
+ unsigned int ssa_count, temp_count, indexable_temp_count;
/* Number of threads to be executed (on the X, Y, and Z dimensions) in a single thread group in
* compute shader profiles. It is set using the numthreads() attribute in the entry point. */
@@ -1541,6 +1544,12 @@ static inline bool hlsl_var_has_buffer_offset_register_reservation(struct hlsl_c
return var->reg_reservation.reg_type == 'c' && var->buffer == ctx->globals_buffer;
}
+static inline bool hlsl_is_comparison_op(enum hlsl_ir_expr_op op)
+{
+ return op == HLSL_OP2_EQUAL || op == HLSL_OP2_GEQUAL
+ || op == HLSL_OP2_LESS || op == HLSL_OP2_NEQUAL;
+}
+
char *hlsl_sprintf_alloc(struct hlsl_ctx *ctx, const char *fmt, ...) VKD3D_PRINTF_FUNC(2, 3);
const char *debug_hlsl_expr_op(enum hlsl_ir_expr_op op);
@@ -1693,6 +1702,9 @@ struct hlsl_type *hlsl_new_stream_output_type(struct hlsl_ctx *ctx,
struct hlsl_ir_node *hlsl_new_ternary_expr(struct hlsl_ctx *ctx, enum hlsl_ir_expr_op op,
struct hlsl_ir_node *arg1, struct hlsl_ir_node *arg2, struct hlsl_ir_node *arg3);
+bool hlsl_constant_is_zero(struct hlsl_ir_constant *c);
+bool hlsl_constant_is_one(struct hlsl_ir_constant *c);
+
void hlsl_init_simple_deref_from_var(struct hlsl_deref *deref, struct hlsl_ir_var *var);
struct hlsl_ir_load *hlsl_new_var_load(struct hlsl_ctx *ctx, struct hlsl_ir_var *var,
diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl.l b/libs/vkd3d/libs/vkd3d-shader/hlsl.l
index 0cdebb8a657..da9f0d39136 100644
--- a/libs/vkd3d/libs/vkd3d-shader/hlsl.l
+++ b/libs/vkd3d/libs/vkd3d-shader/hlsl.l
@@ -346,7 +346,7 @@ while {return KW_WHILE; }
<pp>{ANY} {}
{ANY} {
- return yytext[0];
+ return (unsigned char)yytext[0];
}
%%
diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl.y b/libs/vkd3d/libs/vkd3d-shader/hlsl.y
index 024d96c5663..d83ad9fe7d8 100644
--- a/libs/vkd3d/libs/vkd3d-shader/hlsl.y
+++ b/libs/vkd3d/libs/vkd3d-shader/hlsl.y
@@ -3983,6 +3983,53 @@ static bool intrinsic_frac(struct hlsl_ctx *ctx,
return !!add_unary_arithmetic_expr(ctx, params->instrs, HLSL_OP1_FRACT, arg, loc);
}
+static bool intrinsic_frexp(struct hlsl_ctx *ctx,
+ const struct parse_initializer *params, const struct vkd3d_shader_location *loc)
+{
+ struct hlsl_type *type, *uint_dim_type, *int_dim_type, *bool_dim_type;
+ struct hlsl_ir_function_decl *func;
+ char *body;
+
+ static const char template[] =
+ "%s frexp(%s x, out %s exp)\n"
+ "{\n"
+ /* If x is zero, always return zero for exp and mantissa. */
+ " %s is_nonzero_mask = x != 0.0;\n"
+ " %s bits = asuint(x);\n"
+ /* Subtract 126, not 127, to increase the exponent */
+ " %s exp_int = asint((bits & 0x7f800000u) >> 23) - 126;\n"
+ /* Clear the given exponent and replace it with the bit pattern
+ * for 2^-1 */
+ " %s mantissa = asfloat((bits & 0x007fffffu) | 0x3f000000);\n"
+ " exp = is_nonzero_mask * %s(exp_int);\n"
+ " return is_nonzero_mask * mantissa;\n"
+ "}\n";
+
+ if (!elementwise_intrinsic_float_convert_args(ctx, params, loc))
+ return false;
+ type = params->args[0]->data_type;
+
+ if (type->e.numeric.type == HLSL_TYPE_DOUBLE)
+ {
+ hlsl_fixme(ctx, loc, "frexp() on doubles.");
+ return false;
+ }
+ type = hlsl_get_numeric_type(ctx, type->class, HLSL_TYPE_FLOAT, type->e.numeric.dimx, type->e.numeric.dimy);
+ uint_dim_type = hlsl_get_numeric_type(ctx, type->class, HLSL_TYPE_UINT, type->e.numeric.dimx, type->e.numeric.dimy);
+ int_dim_type = hlsl_get_numeric_type(ctx, type->class, HLSL_TYPE_INT, type->e.numeric.dimx, type->e.numeric.dimy);
+ bool_dim_type = hlsl_get_numeric_type(ctx, type->class, HLSL_TYPE_BOOL, type->e.numeric.dimx, type->e.numeric.dimy);
+
+ if (!(body = hlsl_sprintf_alloc(ctx, template, type->name, type->name, type->name,
+ bool_dim_type->name, uint_dim_type->name, int_dim_type->name, type->name, type->name)))
+ return false;
+ func = hlsl_compile_internal_function(ctx, "frexp", body);
+ vkd3d_free(body);
+ if (!func)
+ return false;
+
+ return !!add_user_call(ctx, func, params, false, loc);
+}
+
static bool intrinsic_fwidth(struct hlsl_ctx *ctx,
const struct parse_initializer *params, const struct vkd3d_shader_location *loc)
{
@@ -4701,7 +4748,8 @@ static bool intrinsic_tex(struct hlsl_ctx *ctx, const struct parse_initializer *
}
if (!strcmp(name, "tex2Dbias")
- || !strcmp(name, "tex2Dlod"))
+ || !strcmp(name, "tex2Dlod")
+ || !strcmp(name, "texCUBEbias"))
{
struct hlsl_ir_node *lod, *c;
@@ -4853,6 +4901,12 @@ static bool intrinsic_texCUBE(struct hlsl_ctx *ctx,
return intrinsic_tex(ctx, params, loc, "texCUBE", HLSL_SAMPLER_DIM_CUBE);
}
+static bool intrinsic_texCUBEbias(struct hlsl_ctx *ctx,
+ const struct parse_initializer *params, const struct vkd3d_shader_location *loc)
+{
+ return intrinsic_tex(ctx, params, loc, "texCUBEbias", HLSL_SAMPLER_DIM_CUBE);
+}
+
static bool intrinsic_texCUBEgrad(struct hlsl_ctx *ctx,
const struct parse_initializer *params, const struct vkd3d_shader_location *loc)
{
@@ -5283,6 +5337,7 @@ intrinsic_functions[] =
{"floor", 1, true, intrinsic_floor},
{"fmod", 2, true, intrinsic_fmod},
{"frac", 1, true, intrinsic_frac},
+ {"frexp", 2, true, intrinsic_frexp},
{"fwidth", 1, true, intrinsic_fwidth},
{"isinf", 1, true, intrinsic_isinf},
{"ldexp", 2, true, intrinsic_ldexp},
@@ -5327,6 +5382,7 @@ intrinsic_functions[] =
{"tex3Dgrad", 4, false, intrinsic_tex3Dgrad},
{"tex3Dproj", 2, false, intrinsic_tex3Dproj},
{"texCUBE", -1, false, intrinsic_texCUBE},
+ {"texCUBEbias", 2, false, intrinsic_texCUBEbias},
{"texCUBEgrad", 4, false, intrinsic_texCUBEgrad},
{"texCUBEproj", 2, false, intrinsic_texCUBEproj},
{"transpose", 1, true, intrinsic_transpose},
@@ -8059,7 +8115,7 @@ resource_format:
{
uint32_t modifiers = $1;
- if (!($$ = apply_type_modifiers(ctx, $2, &modifiers, false, &@1)))
+ if (!($$ = apply_type_modifiers(ctx, $2, &modifiers, true, &@1)))
YYABORT;
}
diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c b/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c
index 0b3dee4d2ce..eaf7d7a3d63 100644
--- a/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c
+++ b/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c
@@ -175,12 +175,29 @@ static unsigned int hlsl_type_get_packed_size(const struct hlsl_type *type)
}
}
+static unsigned int struct_field_get_packed_offset(const struct hlsl_type *record, unsigned int field_idx)
+{
+ unsigned int offset = 0;
+
+ VKD3D_ASSERT(record->class == HLSL_CLASS_STRUCT);
+ VKD3D_ASSERT(field_idx < record->e.record.field_count);
+
+ for (unsigned int i = 0; i < field_idx; ++i)
+ {
+ struct hlsl_struct_field *field = &record->e.record.fields[i];
+ offset = align(offset, hlsl_type_get_packed_alignment(field->type)) + hlsl_type_get_packed_size(field->type);
+ }
+
+ return align(offset, hlsl_type_get_packed_alignment(record->e.record.fields[field_idx].type));
+}
+
+
static struct hlsl_ir_node *hlsl_block_add_packed_index_offset_append(struct hlsl_ctx *ctx,
struct hlsl_block *block, struct hlsl_ir_node *prev_offset, struct hlsl_ir_node *idx,
struct hlsl_type *type, const struct vkd3d_shader_location *loc)
{
struct hlsl_ir_node *idx_offset = NULL, *c;
- unsigned int field_idx, offset, size, i;
+ unsigned int field_idx, offset, size;
switch (type->class)
{
@@ -203,15 +220,7 @@ static struct hlsl_ir_node *hlsl_block_add_packed_index_offset_append(struct hls
case HLSL_CLASS_STRUCT:
field_idx = hlsl_ir_constant(idx)->value.u[0].u;
- for (i = 0, offset = 0; i < field_idx; ++i)
- {
- struct hlsl_struct_field *field = &type->e.record.fields[i];
-
- offset = align(offset, hlsl_type_get_packed_alignment(field->type))
- + hlsl_type_get_packed_size(field->type);
- }
-
- offset = align(offset, hlsl_type_get_packed_alignment(type->e.record.fields[field_idx].type));
+ offset = struct_field_get_packed_offset(type, field_idx);
idx_offset = hlsl_block_add_uint_constant(ctx, block, offset, loc);
break;
@@ -5029,8 +5038,7 @@ static bool lower_comparison_operators(struct hlsl_ctx *ctx, struct hlsl_ir_node
if (instr->type != HLSL_IR_EXPR)
return false;
expr = hlsl_ir_expr(instr);
- if (expr->op != HLSL_OP2_EQUAL && expr->op != HLSL_OP2_NEQUAL && expr->op != HLSL_OP2_LESS
- && expr->op != HLSL_OP2_GEQUAL)
+ if (!hlsl_is_comparison_op(expr->op))
return false;
arg1 = expr->operands[0].node;
@@ -5906,11 +5914,13 @@ static void mark_vars_usage(struct hlsl_ctx *ctx)
struct register_allocator
{
+ /* Type of registers we are allocating (not counting indexable temps). */
+ enum vkd3d_shader_register_type type;
+
struct allocation
{
uint32_t reg;
unsigned int writemask;
- unsigned int first_write, last_read;
/* Two allocations with different mode can't share the same register. */
int mode;
@@ -5920,11 +5930,7 @@ struct register_allocator
} *allocations;
size_t count, capacity;
- /* Indexable temps are allocated separately and always keep their index regardless of their
- * lifetime. */
- uint32_t indexable_count;
-
- /* Total number of registers allocated so far. Used to declare sm4 temp count. */
+ /* Total number of registers allocated so far. */
uint32_t reg_count;
/* Special flag so allocations that can share registers prioritize those
@@ -5936,7 +5942,7 @@ struct register_allocator
};
static unsigned int get_available_writemask(const struct register_allocator *allocator,
- unsigned int first_write, unsigned int last_read, uint32_t reg_idx, int mode, bool vip)
+ uint32_t reg_idx, int mode, bool vip)
{
unsigned int writemask = VKD3DSP_WRITEMASK_ALL;
size_t i;
@@ -5945,12 +5951,7 @@ static unsigned int get_available_writemask(const struct register_allocator *all
{
const struct allocation *allocation = &allocator->allocations[i];
- /* We do not overlap if first write == last read:
- * this is the case where we are allocating the result of that
- * expression, e.g. "add r0, r0, r1". */
-
- if (allocation->reg == reg_idx
- && first_write < allocation->last_read && last_read > allocation->first_write)
+ if (allocation->reg == reg_idx)
{
writemask &= ~allocation->writemask;
if (allocation->mode != mode)
@@ -5967,7 +5968,7 @@ static unsigned int get_available_writemask(const struct register_allocator *all
}
static void record_allocation(struct hlsl_ctx *ctx, struct register_allocator *allocator, uint32_t reg_idx,
- unsigned int writemask, unsigned int first_write, unsigned int last_read, int mode, bool vip)
+ unsigned int writemask, int mode, bool vip)
{
struct allocation *allocation;
@@ -5978,8 +5979,6 @@ static void record_allocation(struct hlsl_ctx *ctx, struct register_allocator *a
allocation = &allocator->allocations[allocator->count++];
allocation->reg = reg_idx;
allocation->writemask = writemask;
- allocation->first_write = first_write;
- allocation->last_read = last_read;
allocation->mode = mode;
allocation->vip = vip;
@@ -5998,8 +5997,7 @@ static void record_allocation(struct hlsl_ctx *ctx, struct register_allocator *a
* 'vip' can be used so that no new allocations can be made in the given register
* unless they are 'vip' as well. */
static struct hlsl_reg allocate_register(struct hlsl_ctx *ctx, struct register_allocator *allocator,
- unsigned int first_write, unsigned int last_read, unsigned int reg_size,
- unsigned int component_count, int mode, bool force_align, bool vip)
+ unsigned int reg_size, unsigned int component_count, int mode, bool force_align, bool vip)
{
struct hlsl_reg ret = {.allocation_size = 1, .allocated = true};
unsigned int required_size = force_align ? 4 : reg_size;
@@ -6012,62 +6010,34 @@ static struct hlsl_reg allocate_register(struct hlsl_ctx *ctx, struct register_a
{
for (uint32_t reg_idx = 0; reg_idx < allocator->reg_count; ++reg_idx)
{
- unsigned int available_writemask = get_available_writemask(allocator,
- first_write, last_read, reg_idx, mode, vip);
+ unsigned int available_writemask = get_available_writemask(allocator, reg_idx, mode, vip);
if (vkd3d_popcount(available_writemask) >= pref)
{
unsigned int writemask = hlsl_combine_writemasks(available_writemask,
vkd3d_write_mask_from_component_count(reg_size));
- ret.type = VKD3DSPR_TEMP;
+ ret.type = allocator->type;
ret.id = reg_idx;
ret.writemask = hlsl_combine_writemasks(writemask,
vkd3d_write_mask_from_component_count(component_count));
- record_allocation(ctx, allocator, reg_idx, writemask, first_write, last_read, mode, vip);
+ record_allocation(ctx, allocator, reg_idx, writemask, mode, vip);
return ret;
}
}
}
- ret.type = VKD3DSPR_TEMP;
+ ret.type = allocator->type;
ret.id = allocator->reg_count;
ret.writemask = vkd3d_write_mask_from_component_count(component_count);
record_allocation(ctx, allocator, allocator->reg_count,
- vkd3d_write_mask_from_component_count(reg_size), first_write, last_read, mode, vip);
+ vkd3d_write_mask_from_component_count(reg_size), mode, vip);
return ret;
}
-/* Allocate a register with writemask, while reserving reg_writemask. */
-static struct hlsl_reg allocate_register_with_masks(struct hlsl_ctx *ctx,
- struct register_allocator *allocator, unsigned int first_write, unsigned int last_read,
- uint32_t reg_writemask, uint32_t writemask, int mode, bool vip)
-{
- struct hlsl_reg ret = {0};
- uint32_t reg_idx;
-
- VKD3D_ASSERT((reg_writemask & writemask) == writemask);
-
- for (reg_idx = 0;; ++reg_idx)
- {
- if ((get_available_writemask(allocator, first_write, last_read,
- reg_idx, mode, vip) & reg_writemask) == reg_writemask)
- break;
- }
-
- record_allocation(ctx, allocator, reg_idx, reg_writemask, first_write, last_read, mode, vip);
-
- ret.type = VKD3DSPR_TEMP;
- ret.id = reg_idx;
- ret.allocation_size = 1;
- ret.writemask = writemask;
- ret.allocated = true;
- return ret;
-}
-
-static bool is_range_available(const struct register_allocator *allocator, unsigned int first_write,
- unsigned int last_read, uint32_t reg_idx, unsigned int reg_size, int mode, bool vip)
+static bool is_range_available(const struct register_allocator *allocator,
+ uint32_t reg_idx, unsigned int reg_size, int mode, bool vip)
{
unsigned int last_reg_mask = (1u << (reg_size % 4)) - 1;
unsigned int writemask;
@@ -6075,18 +6045,18 @@ static bool is_range_available(const struct register_allocator *allocator, unsig
for (i = 0; i < (reg_size / 4); ++i)
{
- writemask = get_available_writemask(allocator, first_write, last_read, reg_idx + i, mode, vip);
+ writemask = get_available_writemask(allocator, reg_idx + i, mode, vip);
if (writemask != VKD3DSP_WRITEMASK_ALL)
return false;
}
- writemask = get_available_writemask(allocator, first_write, last_read, reg_idx + (reg_size / 4), mode, vip);
+ writemask = get_available_writemask(allocator, reg_idx + (reg_size / 4), mode, vip);
if ((writemask & last_reg_mask) != last_reg_mask)
return false;
return true;
}
-static struct hlsl_reg allocate_range(struct hlsl_ctx *ctx, struct register_allocator *allocator,
- unsigned int first_write, unsigned int last_read, unsigned int reg_size, int mode, bool vip)
+static struct hlsl_reg allocate_range(struct hlsl_ctx *ctx,
+ struct register_allocator *allocator, unsigned int reg_size, int mode, bool vip)
{
struct hlsl_reg ret = {0};
uint32_t reg_idx;
@@ -6094,35 +6064,33 @@ static struct hlsl_reg allocate_range(struct hlsl_ctx *ctx, struct register_allo
for (reg_idx = 0;; ++reg_idx)
{
- if (is_range_available(allocator, first_write, last_read, reg_idx, reg_size, mode, vip))
+ if (is_range_available(allocator, reg_idx, reg_size, mode, vip))
break;
}
for (i = 0; i < reg_size / 4; ++i)
- record_allocation(ctx, allocator, reg_idx + i, VKD3DSP_WRITEMASK_ALL, first_write, last_read, mode, vip);
+ record_allocation(ctx, allocator, reg_idx + i, VKD3DSP_WRITEMASK_ALL, mode, vip);
if (reg_size % 4)
- record_allocation(ctx, allocator, reg_idx + (reg_size / 4),
- (1u << (reg_size % 4)) - 1, first_write, last_read, mode, vip);
+ record_allocation(ctx, allocator, reg_idx + (reg_size / 4), (1u << (reg_size % 4)) - 1, mode, vip);
- ret.type = VKD3DSPR_TEMP;
+ ret.type = allocator->type;
ret.id = reg_idx;
ret.allocation_size = align(reg_size, 4) / 4;
ret.allocated = true;
return ret;
}
-static struct hlsl_reg allocate_numeric_registers_for_type(struct hlsl_ctx *ctx, struct register_allocator *allocator,
- unsigned int first_write, unsigned int last_read, const struct hlsl_type *type)
+static struct hlsl_reg allocate_numeric_registers_for_type(struct hlsl_ctx *ctx,
+ struct register_allocator *allocator, const struct hlsl_type *type)
{
unsigned int reg_size = type->reg_size[HLSL_REGSET_NUMERIC];
/* FIXME: We could potentially pack structs or arrays more efficiently... */
if (type->class <= HLSL_CLASS_VECTOR)
- return allocate_register(ctx, allocator, first_write, last_read,
- type->e.numeric.dimx, type->e.numeric.dimx, 0, false, false);
+ return allocate_register(ctx, allocator, type->e.numeric.dimx, type->e.numeric.dimx, 0, false, false);
else
- return allocate_range(ctx, allocator, first_write, last_read, reg_size, 0, false);
+ return allocate_range(ctx, allocator, reg_size, 0, false);
}
static const char *debug_register(struct hlsl_reg reg, const struct hlsl_type *type)
@@ -6287,10 +6255,9 @@ static void calculate_resource_register_counts(struct hlsl_ctx *ctx)
}
}
-static void allocate_instr_temp_register(struct hlsl_ctx *ctx,
- struct hlsl_ir_node *instr, struct register_allocator *allocator)
+static void allocate_instr_temp_register(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr)
{
- unsigned int reg_writemask = 0, dst_writemask = 0;
+ unsigned int dst_writemask = 0;
bool is_per_component = false;
if (instr->reg.allocated || !instr->last_read)
@@ -6302,12 +6269,10 @@ static void allocate_instr_temp_register(struct hlsl_ctx *ctx,
{
case HLSL_OP1_COS_REDUCED:
dst_writemask = VKD3DSP_WRITEMASK_0;
- reg_writemask = ctx->profile->major_version < 3 ? (1 << 3) - 1 : VKD3DSP_WRITEMASK_0;
break;
case HLSL_OP1_SIN_REDUCED:
dst_writemask = VKD3DSP_WRITEMASK_1;
- reg_writemask = ctx->profile->major_version < 3 ? (1 << 3) - 1 : VKD3DSP_WRITEMASK_1;
break;
case HLSL_OP1_EXP2:
@@ -6329,12 +6294,22 @@ static void allocate_instr_temp_register(struct hlsl_ctx *ctx,
VKD3D_ASSERT(instr->data_type->class <= HLSL_CLASS_VECTOR);
- if (reg_writemask)
- instr->reg = allocate_register_with_masks(ctx, allocator,
- instr->index, instr->last_read, reg_writemask, dst_writemask, 0, false);
+ if (dst_writemask)
+ {
+ instr->reg.writemask = dst_writemask;
+ instr->reg.allocation_size = 1;
+ instr->reg.allocated = true;
+ instr->reg.type = VKD3DSPR_TEMP;
+ instr->reg.id = ctx->temp_count++;
+ }
else if (is_per_component)
- instr->reg = allocate_numeric_registers_for_type(ctx, allocator,
- instr->index, instr->last_read, instr->data_type);
+ {
+ instr->reg.writemask = vkd3d_write_mask_from_component_count(instr->data_type->e.numeric.dimx);
+ instr->reg.allocation_size = 1;
+ instr->reg.allocated = true;
+ instr->reg.type = VKD3DSPR_TEMP;
+ instr->reg.id = ctx->temp_count++;
+ }
else
{
instr->reg.writemask = vkd3d_write_mask_from_component_count(instr->data_type->e.numeric.dimx);
@@ -6344,40 +6319,46 @@ static void allocate_instr_temp_register(struct hlsl_ctx *ctx,
instr->reg.id = ctx->ssa_count++;
}
- TRACE("Allocated anonymous expression @%u to %s (liveness %u-%u).\n", instr->index,
- debug_register(instr->reg, instr->data_type), instr->index, instr->last_read);
+ TRACE("Allocated anonymous expression @%u to %s.\n", instr->index,
+ debug_register(instr->reg, instr->data_type));
}
-static void allocate_variable_temp_register(struct hlsl_ctx *ctx,
- struct hlsl_ir_var *var, struct register_allocator *allocator)
+static void allocate_variable_temp_register(struct hlsl_ctx *ctx, struct hlsl_ir_var *var)
{
+ struct hlsl_reg *reg = &var->regs[HLSL_REGSET_NUMERIC];
+
if (var->is_input_semantic || var->is_output_semantic || var->is_uniform)
return;
- if (!var->regs[HLSL_REGSET_NUMERIC].allocated && var->last_read)
+ if (!reg->allocated && var->last_read)
{
if (var->indexable)
{
- var->regs[HLSL_REGSET_NUMERIC].id = allocator->indexable_count++;
- var->regs[HLSL_REGSET_NUMERIC].allocation_size = 1;
- var->regs[HLSL_REGSET_NUMERIC].writemask = 0;
- var->regs[HLSL_REGSET_NUMERIC].allocated = true;
+ reg->id = ctx->indexable_temp_count++;
+ reg->allocation_size = 1;
+ reg->writemask = 0;
+ reg->allocated = true;
- TRACE("Allocated %s to x%u[].\n", var->name, var->regs[HLSL_REGSET_NUMERIC].id);
+ TRACE("Allocated %s to x%u[].\n", var->name, reg->id);
}
else
{
- var->regs[HLSL_REGSET_NUMERIC] = allocate_numeric_registers_for_type(ctx, allocator,
- var->first_write, var->last_read, var->data_type);
+ reg->type = VKD3DSPR_TEMP;
+ reg->id = ctx->temp_count;
+ reg->allocation_size = align(var->data_type->reg_size[HLSL_REGSET_NUMERIC], 4) / 4;
+ if (var->data_type->class <= HLSL_CLASS_VECTOR)
+ reg->writemask = vkd3d_write_mask_from_component_count(var->data_type->e.numeric.dimx);
+ reg->allocated = true;
- TRACE("Allocated %s to %s (liveness %u-%u).\n", var->name,
- debug_register(var->regs[HLSL_REGSET_NUMERIC], var->data_type), var->first_write, var->last_read);
+ ctx->temp_count += reg->allocation_size;
+
+ TRACE("Allocated %s to %s.\n", var->name,
+ debug_register(var->regs[HLSL_REGSET_NUMERIC], var->data_type));
}
}
}
-static void allocate_temp_registers_recurse(struct hlsl_ctx *ctx,
- struct hlsl_block *block, struct register_allocator *allocator)
+static void allocate_temp_registers_recurse(struct hlsl_ctx *ctx, struct hlsl_block *block)
{
struct hlsl_ir_node *instr;
@@ -6387,15 +6368,15 @@ static void allocate_temp_registers_recurse(struct hlsl_ctx *ctx,
if (ctx->profile->major_version >= 4 && instr->type == HLSL_IR_CONSTANT)
continue;
- allocate_instr_temp_register(ctx, instr, allocator);
+ allocate_instr_temp_register(ctx, instr);
switch (instr->type)
{
case HLSL_IR_IF:
{
struct hlsl_ir_if *iff = hlsl_ir_if(instr);
- allocate_temp_registers_recurse(ctx, &iff->then_block, allocator);
- allocate_temp_registers_recurse(ctx, &iff->else_block, allocator);
+ allocate_temp_registers_recurse(ctx, &iff->then_block);
+ allocate_temp_registers_recurse(ctx, &iff->else_block);
break;
}
@@ -6404,21 +6385,21 @@ static void allocate_temp_registers_recurse(struct hlsl_ctx *ctx,
struct hlsl_ir_load *load = hlsl_ir_load(instr);
/* We need to at least allocate a variable for undefs.
* FIXME: We should probably find a way to remove them instead. */
- allocate_variable_temp_register(ctx, load->src.var, allocator);
+ allocate_variable_temp_register(ctx, load->src.var);
break;
}
case HLSL_IR_LOOP:
{
struct hlsl_ir_loop *loop = hlsl_ir_loop(instr);
- allocate_temp_registers_recurse(ctx, &loop->body, allocator);
+ allocate_temp_registers_recurse(ctx, &loop->body);
break;
}
case HLSL_IR_STORE:
{
struct hlsl_ir_store *store = hlsl_ir_store(instr);
- allocate_variable_temp_register(ctx, store->lhs.var, allocator);
+ allocate_variable_temp_register(ctx, store->lhs.var);
break;
}
@@ -6429,7 +6410,7 @@ static void allocate_temp_registers_recurse(struct hlsl_ctx *ctx,
LIST_FOR_EACH_ENTRY(c, &s->cases, struct hlsl_ir_switch_case, entry)
{
- allocate_temp_registers_recurse(ctx, &c->body, allocator);
+ allocate_temp_registers_recurse(ctx, &c->body);
}
break;
}
@@ -6553,8 +6534,7 @@ static void allocate_const_registers_recurse(struct hlsl_ctx *ctx,
break;
}
- constant->reg = allocate_numeric_registers_for_type(ctx, allocator, 1, UINT_MAX, type);
- constant->reg.type = VKD3DSPR_CONST;
+ constant->reg = allocate_numeric_registers_for_type(ctx, allocator, type);
TRACE("Allocated constant @%u to %s.\n", instr->index, debug_register(constant->reg, type));
for (unsigned int x = 0, i = 0; x < 4; ++x)
@@ -6651,16 +6631,14 @@ static void allocate_sincos_const_registers(struct hlsl_ctx *ctx, struct hlsl_bl
{
type = hlsl_get_vector_type(ctx, HLSL_TYPE_FLOAT, 4);
- ctx->d3dsincosconst1 = allocate_numeric_registers_for_type(ctx, allocator, 1, UINT_MAX, type);
- ctx->d3dsincosconst1.type = VKD3DSPR_CONST;
+ ctx->d3dsincosconst1 = allocate_numeric_registers_for_type(ctx, allocator, type);
TRACE("Allocated D3DSINCOSCONST1 to %s.\n", debug_register(ctx->d3dsincosconst1, type));
record_constant(ctx, ctx->d3dsincosconst1.id * 4 + 0, -1.55009923e-06f, &instr->loc);
record_constant(ctx, ctx->d3dsincosconst1.id * 4 + 1, -2.17013894e-05f, &instr->loc);
record_constant(ctx, ctx->d3dsincosconst1.id * 4 + 2, 2.60416674e-03f, &instr->loc);
record_constant(ctx, ctx->d3dsincosconst1.id * 4 + 3, 2.60416680e-04f, &instr->loc);
- ctx->d3dsincosconst2 = allocate_numeric_registers_for_type(ctx, allocator, 1, UINT_MAX, type);
- ctx->d3dsincosconst2.type = VKD3DSPR_CONST;
+ ctx->d3dsincosconst2 = allocate_numeric_registers_for_type(ctx, allocator, type);
TRACE("Allocated D3DSINCOSCONST2 to %s.\n", debug_register(ctx->d3dsincosconst2, type));
record_constant(ctx, ctx->d3dsincosconst2.id * 4 + 0, -2.08333340e-02f, &instr->loc);
record_constant(ctx, ctx->d3dsincosconst2.id * 4 + 1, -1.25000000e-01f, &instr->loc);
@@ -6674,8 +6652,7 @@ static void allocate_sincos_const_registers(struct hlsl_ctx *ctx, struct hlsl_bl
static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_block *body)
{
- struct register_allocator allocator_used = {0};
- struct register_allocator allocator = {0};
+ struct register_allocator allocator = {.type = VKD3DSPR_CONST}, allocator_used = {.type = VKD3DSPR_CONST};
struct hlsl_ir_var *var;
sort_uniforms_by_bind_count(ctx, HLSL_REGSET_NUMERIC);
@@ -6698,15 +6675,14 @@ static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_block *bo
{
if (i < bind_count)
{
- if (get_available_writemask(&allocator_used, 1, UINT_MAX,
- reg_idx + i, 0, false) != VKD3DSP_WRITEMASK_ALL)
+ if (get_available_writemask(&allocator_used, reg_idx + i, 0, false) != VKD3DSP_WRITEMASK_ALL)
{
hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_RESERVATION,
"Overlapping register() reservations on 'c%u'.", reg_idx + i);
}
- record_allocation(ctx, &allocator_used, reg_idx + i, VKD3DSP_WRITEMASK_ALL, 1, UINT_MAX, 0, false);
+ record_allocation(ctx, &allocator_used, reg_idx + i, VKD3DSP_WRITEMASK_ALL, 0, false);
}
- record_allocation(ctx, &allocator, reg_idx + i, VKD3DSP_WRITEMASK_ALL, 1, UINT_MAX, 0, false);
+ record_allocation(ctx, &allocator, reg_idx + i, VKD3DSP_WRITEMASK_ALL, 0, false);
}
var->regs[HLSL_REGSET_NUMERIC].type = VKD3DSPR_CONST;
@@ -6730,8 +6706,7 @@ static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_block *bo
if (!var->regs[HLSL_REGSET_NUMERIC].allocated)
{
- var->regs[HLSL_REGSET_NUMERIC] = allocate_range(ctx, &allocator, 1, UINT_MAX, alloc_size, 0, false);
- var->regs[HLSL_REGSET_NUMERIC].type = VKD3DSPR_CONST;
+ var->regs[HLSL_REGSET_NUMERIC] = allocate_range(ctx, &allocator, alloc_size, 0, false);
TRACE("Allocated %s to %s.\n", var->name,
debug_register(var->regs[HLSL_REGSET_NUMERIC], var->data_type));
}
@@ -6748,12 +6723,13 @@ static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_block *bo
* index to all (simultaneously live) variables or intermediate values. Agnostic
* as to how many registers are actually available for the current backend, and
* does not handle constants. */
-static uint32_t allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_block *body, struct list *semantic_vars)
+static void allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_block *body, struct list *semantic_vars)
{
- struct register_allocator allocator = {0};
struct hlsl_scope *scope;
struct hlsl_ir_var *var;
+ ctx->indexable_temp_count = 0;
+
/* Reset variable temp register allocations. */
LIST_FOR_EACH_ENTRY(scope, &ctx->scopes, struct hlsl_scope, entry)
{
@@ -6771,25 +6747,13 @@ static uint32_t allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_block
{
if (var->is_output_semantic)
{
- record_allocation(ctx, &allocator, 0, VKD3DSP_WRITEMASK_ALL,
- var->first_write, UINT_MAX, 0, false);
+ ctx->temp_count = 1;
break;
}
}
}
- allocate_temp_registers_recurse(ctx, body, &allocator);
- vkd3d_free(allocator.allocations);
-
- if (allocator.indexable_count)
- TRACE("Declaration of %s function required %u temp registers, and %u indexable temps.\n",
- ctx->is_patch_constant_func ? "patch constant" : "main",
- allocator.reg_count, allocator.indexable_count);
- else
- TRACE("Declaration of %s function required %u temp registers.\n",
- ctx->is_patch_constant_func ? "patch constant" : "main", allocator.reg_count);
-
- return allocator.reg_count;
+ allocate_temp_registers_recurse(ctx, body);
}
static enum vkd3d_shader_interpolation_mode sm4_get_interpolation_mode(struct hlsl_type *type,
@@ -6928,9 +6892,8 @@ static void allocate_semantic_register(struct hlsl_ctx *ctx, struct hlsl_ir_var
if (special_interpolation)
mode = VKD3DSIM_NONE;
- var->regs[HLSL_REGSET_NUMERIC] = allocate_register(ctx, allocator, 1, UINT_MAX,
+ var->regs[HLSL_REGSET_NUMERIC] = allocate_register(ctx, allocator,
reg_size, component_count, mode, var->force_align, vip_allocation);
- var->regs[HLSL_REGSET_NUMERIC].type = output ? VKD3DSPR_OUTPUT : VKD3DSPR_INPUT;
TRACE("Allocated %s to %s (mode %d).\n", var->name,
debug_register(var->regs[HLSL_REGSET_NUMERIC], var->data_type), mode);
@@ -6945,11 +6908,17 @@ static void allocate_semantic_registers(struct hlsl_ctx *ctx, struct list *seman
bool is_pixel_shader = ctx->profile->type == VKD3D_SHADER_TYPE_PIXEL;
struct hlsl_ir_var *var;
+ in_prim_allocator.type = VKD3DSPR_INPUT;
in_prim_allocator.prioritize_smaller_writemasks = true;
+ patch_constant_out_patch_allocator.type = VKD3DSPR_INPUT;
patch_constant_out_patch_allocator.prioritize_smaller_writemasks = true;
+ input_allocator.type = VKD3DSPR_INPUT;
input_allocator.prioritize_smaller_writemasks = true;
for (unsigned int i = 0; i < ARRAY_SIZE(output_allocators); ++i)
+ {
+ output_allocators[i].type = VKD3DSPR_OUTPUT;
output_allocators[i].prioritize_smaller_writemasks = true;
+ }
LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry)
{
@@ -8266,6 +8235,282 @@ void hlsl_lower_index_loads(struct hlsl_ctx *ctx, struct hlsl_block *body)
lower_ir(ctx, lower_index_loads, body);
}
+static enum hlsl_ir_expr_op invert_comparison_op(enum hlsl_ir_expr_op op)
+{
+ switch (op)
+ {
+ case HLSL_OP2_EQUAL:
+ return HLSL_OP2_NEQUAL;
+
+ case HLSL_OP2_GEQUAL:
+ return HLSL_OP2_LESS;
+
+ case HLSL_OP2_LESS:
+ return HLSL_OP2_GEQUAL;
+
+ case HLSL_OP2_NEQUAL:
+ return HLSL_OP2_EQUAL;
+
+ default:
+ vkd3d_unreachable();
+ }
+}
+
+static bool fold_unary_identities(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr, void *context)
+{
+ struct hlsl_ir_node *res = NULL;
+ struct hlsl_ir_expr *expr, *x;
+
+ if (instr->type != HLSL_IR_EXPR)
+ return false;
+
+ if (instr->data_type->class > HLSL_CLASS_VECTOR)
+ return false;
+
+ expr = hlsl_ir_expr(instr);
+ if (!expr->operands[0].node)
+ return false;
+
+ if (expr->operands[0].node->type != HLSL_IR_EXPR)
+ return false;
+ x = hlsl_ir_expr(expr->operands[0].node);
+
+ switch (expr->op)
+ {
+ case HLSL_OP1_ABS:
+ if (x->op == HLSL_OP1_ABS)
+ {
+ /* ||x|| -> |x| */
+ hlsl_replace_node(instr, &x->node);
+ return true;
+ }
+
+ if (x->op == HLSL_OP1_NEG)
+ {
+ /* |-x| -> |x| */
+ hlsl_src_remove(&expr->operands[0]);
+ hlsl_src_from_node(&expr->operands[0], x->operands[0].node);
+ return true;
+ }
+ break;
+
+ case HLSL_OP1_BIT_NOT:
+ if (x->op == HLSL_OP1_BIT_NOT)
+ {
+ /* ~(~x) -> x */
+ hlsl_replace_node(instr, x->operands[0].node);
+ return true;
+ }
+ break;
+
+ case HLSL_OP1_CEIL:
+ case HLSL_OP1_FLOOR:
+ if (x->op == HLSL_OP1_CEIL || x->op == HLSL_OP1_FLOOR)
+ {
+ /* f(g(x)) -> g(x), where f(), g() are floor() or ceil() functions. */
+ hlsl_replace_node(instr, &x->node);
+ return true;
+ }
+ break;
+
+ case HLSL_OP1_NEG:
+ if (x->op == HLSL_OP1_NEG)
+ {
+ /* -(-x) -> x */
+ hlsl_replace_node(instr, x->operands[0].node);
+ return true;
+ }
+ break;
+
+ case HLSL_OP1_LOGIC_NOT:
+ if (x->op == HLSL_OP1_LOGIC_NOT)
+ {
+ /* !!x -> x */
+ hlsl_replace_node(instr, x->operands[0].node);
+ return true;
+ }
+
+ if (hlsl_is_comparison_op(x->op)
+ && hlsl_base_type_is_integer(x->operands[0].node->data_type->e.numeric.type)
+ && hlsl_base_type_is_integer(x->operands[1].node->data_type->e.numeric.type))
+ {
+ struct hlsl_ir_node *operands[HLSL_MAX_OPERANDS] = {x->operands[0].node, x->operands[1].node};
+ struct hlsl_block block;
+
+ hlsl_block_init(&block);
+
+ /* !(x == y) -> x != y, !(x < y) -> x >= y, etc. */
+ res = hlsl_block_add_expr(ctx, &block, invert_comparison_op(x->op),
+ operands, instr->data_type, &instr->loc);
+
+ list_move_before(&instr->entry, &block.instrs);
+ hlsl_replace_node(instr, res);
+ return true;
+ }
+
+ break;
+
+ default:
+ break;
+ }
+
+ return false;
+}
+
+static bool nodes_are_equivalent(const struct hlsl_ir_node *c1, const struct hlsl_ir_node *c2)
+{
+ if (c1 == c2)
+ return true;
+
+ if (c1->type == HLSL_IR_SWIZZLE && c2->type == HLSL_IR_SWIZZLE
+ && hlsl_types_are_equal(c1->data_type, c2->data_type))
+ {
+ const struct hlsl_ir_swizzle *s1 = hlsl_ir_swizzle(c1), *s2 = hlsl_ir_swizzle(c2);
+
+ VKD3D_ASSERT(c1->data_type->class <= HLSL_CLASS_VECTOR);
+
+ if (s1->val.node == s2->val.node && s1->u.vector == s2->u.vector)
+ return true;
+ }
+
+ return false;
+}
+
+/* Replaces all conditionals in an expression chain of the form (cond ? x : y)
+ * with x or y, assuming cond = cond_value. */
+static struct hlsl_ir_node *evaluate_conditionals_recurse(struct hlsl_ctx *ctx,
+ struct hlsl_block *block, const struct hlsl_ir_node *cond, bool cond_value,
+ struct hlsl_ir_node *instr, const struct vkd3d_shader_location *loc)
+{
+ struct hlsl_ir_node *operands[HLSL_MAX_OPERANDS] = {0};
+ struct hlsl_ir_expr *expr;
+ struct hlsl_ir_node *res;
+ bool progress = false;
+ unsigned int i;
+
+ if (instr->type != HLSL_IR_EXPR)
+ return NULL;
+ expr = hlsl_ir_expr(instr);
+
+ if (expr->op == HLSL_OP3_TERNARY && nodes_are_equivalent(cond, expr->operands[0].node))
+ {
+ struct hlsl_ir_node *x = cond_value ? expr->operands[1].node : expr->operands[2].node;
+
+ res = evaluate_conditionals_recurse(ctx, block, cond, cond_value, x, loc);
+ return res ? res : x;
+ }
+
+ for (i = 0; i < HLSL_MAX_OPERANDS; ++i)
+ {
+ if (!expr->operands[i].node)
+ break;
+
+ operands[i] = evaluate_conditionals_recurse(ctx, block, cond, cond_value, expr->operands[i].node, loc);
+
+ if (operands[i])
+ progress = true;
+ else
+ operands[i] = expr->operands[i].node;
+ }
+
+ if (progress)
+ return hlsl_block_add_expr(ctx, block, expr->op, operands, expr->node.data_type, loc);
+
+ return NULL;
+}
+
+static bool fold_conditional_identities(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr, void *context)
+{
+ struct hlsl_ir_node *c, *x, *y, *res_x, *res_y;
+ struct hlsl_ir_node *res = NULL;
+ struct hlsl_ir_expr *expr, *ec;
+ struct hlsl_block block;
+
+ if (instr->type != HLSL_IR_EXPR)
+ return false;
+
+ if (instr->data_type->class > HLSL_CLASS_VECTOR)
+ return false;
+
+ expr = hlsl_ir_expr(instr);
+ if (expr->op != HLSL_OP3_TERNARY)
+ return false;
+
+ c = expr->operands[0].node;
+ x = expr->operands[1].node;
+ y = expr->operands[2].node;
+
+ VKD3D_ASSERT(c->data_type->e.numeric.type == HLSL_TYPE_BOOL);
+
+ if (nodes_are_equivalent(x, y))
+ {
+ /* c ? x : x -> x */
+ hlsl_replace_node(instr, x);
+ return true;
+ }
+
+ if (c->type == HLSL_IR_CONSTANT)
+ {
+ if (hlsl_constant_is_zero(hlsl_ir_constant(c)))
+ {
+ /* false ? x : y -> y */
+ hlsl_replace_node(instr, y);
+ return true;
+ }
+
+ if (hlsl_constant_is_one(hlsl_ir_constant(c)))
+ {
+ /* true ? x : y -> x */
+ hlsl_replace_node(instr, x);
+ return true;
+ }
+ }
+
+ hlsl_block_init(&block);
+
+ if (x->type == HLSL_IR_CONSTANT && y->type == HLSL_IR_CONSTANT
+ && hlsl_types_are_equal(c->data_type, x->data_type)
+ && hlsl_types_are_equal(c->data_type, y->data_type))
+ {
+ if (hlsl_constant_is_one(hlsl_ir_constant(x)) && hlsl_constant_is_zero(hlsl_ir_constant(y)))
+ {
+ /* c ? true : false -> c */
+ res = c;
+ goto done;
+ }
+
+ if (hlsl_constant_is_zero(hlsl_ir_constant(x)) && hlsl_constant_is_one(hlsl_ir_constant(y)))
+ {
+ /* c ? false : true -> !c */
+ res = hlsl_block_add_unary_expr(ctx, &block, HLSL_OP1_LOGIC_NOT, c, &instr->loc);
+ goto done;
+ }
+ }
+
+ ec = c->type == HLSL_IR_EXPR ? hlsl_ir_expr(c) : NULL;
+ if (ec && ec->op == HLSL_OP1_LOGIC_NOT)
+ {
+ /* !c ? x : y -> c ? y : x */
+ res = hlsl_add_conditional(ctx, &block, ec->operands[0].node, y, x);
+ goto done;
+ }
+
+ res_x = evaluate_conditionals_recurse(ctx, &block, c, true, x, &instr->loc);
+ res_y = evaluate_conditionals_recurse(ctx, &block, c, false, y, &instr->loc);
+ if (res_x || res_y)
+ res = hlsl_add_conditional(ctx, &block, c, res_x ? res_x : x, res_y ? res_y : y);
+
+done:
+ if (res)
+ {
+ list_move_before(&instr->entry, &block.instrs);
+ hlsl_replace_node(instr, res);
+ return true;
+ }
+
+ hlsl_block_cleanup(&block);
+ return false;
+}
static bool simplify_exprs(struct hlsl_ctx *ctx, struct hlsl_block *block)
{
@@ -8275,6 +8520,8 @@ static bool simplify_exprs(struct hlsl_ctx *ctx, struct hlsl_block *block)
{
progress = hlsl_transform_ir(ctx, hlsl_fold_constant_exprs, block, NULL);
progress |= hlsl_transform_ir(ctx, hlsl_normalize_binary_exprs, block, NULL);
+ progress |= hlsl_transform_ir(ctx, fold_unary_identities, block, NULL);
+ progress |= hlsl_transform_ir(ctx, fold_conditional_identities, block, NULL);
progress |= hlsl_transform_ir(ctx, hlsl_fold_constant_identities, block, NULL);
progress |= hlsl_transform_ir(ctx, hlsl_fold_constant_swizzles, block, NULL);
@@ -8448,6 +8695,7 @@ static void generate_vsir_signature_entry(struct hlsl_ctx *ctx, struct vsir_prog
if (!ascii_strcasecmp(var->semantic.name, "PSIZE") && output
&& program->shader_version.type == VKD3D_SHADER_TYPE_VERTEX)
{
+ program->has_point_size = true;
if (var->data_type->e.numeric.dimx > 1)
hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SEMANTIC,
"PSIZE output must have only 1 component in this shader model.");
@@ -8570,9 +8818,8 @@ static enum vsir_data_type vsir_data_type_from_hlsl_type(struct hlsl_ctx *ctx, c
case HLSL_TYPE_DOUBLE:
return VSIR_DATA_F64;
case HLSL_TYPE_FLOAT:
- return VSIR_DATA_F32;
case HLSL_TYPE_HALF:
- return VSIR_DATA_F16;
+ return VSIR_DATA_F32;
case HLSL_TYPE_INT:
return VSIR_DATA_I32;
case HLSL_TYPE_UINT:
@@ -8703,7 +8950,7 @@ static void sm1_generate_vsir_sampler_dcls(struct hlsl_ctx *ctx,
semantic->resource_type = resource_type;
dst_param = &semantic->resource.reg;
- vsir_register_init(&dst_param->reg, VKD3DSPR_SAMPLER, VSIR_DATA_F32, 1);
+ vsir_register_init(&dst_param->reg, VKD3DSPR_COMBINED_SAMPLER, VSIR_DATA_F32, 1);
dst_param->reg.dimension = VSIR_DIMENSION_NONE;
dst_param->reg.idx[0].offset = var->regs[HLSL_REGSET_SAMPLERS].index + i;
dst_param->write_mask = 0;
@@ -9467,8 +9714,6 @@ static bool sm1_generate_vsir_instr_expr(struct hlsl_ctx *ctx, struct vsir_progr
break;
case HLSL_OP3_CMP:
- if (!hlsl_type_is_floating_point(type))
- goto err;
generate_vsir_instr_expr_single_instr_op(ctx, program, expr, VSIR_OP_CMP, 0, 0, true);
break;
@@ -9930,10 +10175,14 @@ static void sm1_generate_vsir(struct hlsl_ctx *ctx, const struct vkd3d_shader_co
struct hlsl_ir_function_decl *func, struct list *semantic_vars,
struct hlsl_block *body, uint64_t config_flags, struct vsir_program *program)
{
+ struct hlsl_ir_var *var;
struct hlsl_block block;
+ struct hlsl_reg *reg;
+ unsigned int *count;
program->ssa_count = 0;
- program->temp_count = allocate_temp_registers(ctx, body, semantic_vars);
+ program->temp_count = 0;
+ allocate_temp_registers(ctx, body, semantic_vars);
if (ctx->result)
return;
@@ -9944,7 +10193,19 @@ static void sm1_generate_vsir(struct hlsl_ctx *ctx, const struct vkd3d_shader_co
sm1_generate_vsir_block(ctx, body, program);
+ count = &program->flat_constant_count[VKD3D_SHADER_D3DBC_FLOAT_CONSTANT_REGISTER];
+ LIST_FOR_EACH_ENTRY(var, &ctx->extern_vars, struct hlsl_ir_var, extern_entry)
+ {
+ if (!var->is_uniform)
+ continue;
+
+ if (!(reg = &var->regs[HLSL_REGSET_NUMERIC])->allocation_size)
+ continue;
+
+ *count = max(*count, reg->id + reg->allocation_size);
+ }
program->ssa_count = ctx->ssa_count;
+ program->temp_count = ctx->temp_count;
if (ctx->result)
return;
@@ -11437,6 +11698,7 @@ static bool sm4_generate_vsir_instr_ld(struct hlsl_ctx *ctx,
const struct vkd3d_shader_version *version = &program->shader_version;
const struct hlsl_ir_node *sample_index = load->sample_index.node;
const struct hlsl_ir_node *texel_offset = load->texel_offset.node;
+ const struct hlsl_ir_node *byte_offset = load->byte_offset.node;
const struct hlsl_ir_node *coords = load->coords.node;
unsigned int coords_writemask = VKD3DSP_WRITEMASK_ALL;
const struct hlsl_deref *resource = &load->resource;
@@ -11444,20 +11706,15 @@ static bool sm4_generate_vsir_instr_ld(struct hlsl_ctx *ctx,
enum hlsl_sampler_dim dim = load->sampling_dim;
bool tgsm = load->resource.var->is_tgsm;
struct vkd3d_shader_instruction *ins;
+ bool multisampled, raw, structured;
enum vkd3d_shader_opcode opcode;
- bool multisampled, raw;
VKD3D_ASSERT(load->load_type == HLSL_RESOURCE_LOAD);
- if (resource_type->sampler_dim == HLSL_SAMPLER_DIM_STRUCTURED_BUFFER)
- {
- hlsl_fixme(ctx, &load->node.loc, "Structured buffer loads.");
- return false;
- }
-
multisampled = resource_type->class == HLSL_CLASS_TEXTURE
&& (resource_type->sampler_dim == HLSL_SAMPLER_DIM_2DMS
|| resource_type->sampler_dim == HLSL_SAMPLER_DIM_2DMSARRAY);
+ structured = resource_type->sampler_dim == HLSL_SAMPLER_DIM_STRUCTURED_BUFFER;
if (!tgsm)
{
@@ -11468,15 +11725,19 @@ static bool sm4_generate_vsir_instr_ld(struct hlsl_ctx *ctx,
hlsl_fixme(ctx, &load->node.loc, "Load from structured TGSM.");
return false;
}
+ VKD3D_ASSERT(!(structured && multisampled));
- if (uav)
+ if (structured)
+ opcode = VSIR_OP_LD_STRUCTURED;
+ else if (uav)
opcode = VSIR_OP_LD_UAV_TYPED;
else if (raw)
opcode = VSIR_OP_LD_RAW;
else
opcode = multisampled ? VSIR_OP_LD2DMS : VSIR_OP_LD;
- if (!(ins = generate_vsir_add_program_instruction(ctx, program, &instr->loc, opcode, 1, 2 + multisampled)))
+ if (!(ins = generate_vsir_add_program_instruction(ctx, program,
+ &instr->loc, opcode, 1, 2 + multisampled + structured)))
return false;
if (texel_offset && !sm4_generate_vsir_validate_texel_offset_aoffimmi(texel_offset))
@@ -11504,10 +11765,15 @@ static bool sm4_generate_vsir_instr_ld(struct hlsl_ctx *ctx,
vsir_src_from_hlsl_node(&ins->src[0], ctx, coords, coords_writemask);
if (!sm4_generate_vsir_init_src_param_from_deref(ctx, program,
- &ins->src[1], resource, ins->dst[0].write_mask, &instr->loc))
+ &ins->src[structured ? 2 : 1], resource, ins->dst[0].write_mask, &instr->loc))
return false;
- if (multisampled)
+ if (structured)
+ {
+ VKD3D_ASSERT(byte_offset);
+ vsir_src_from_hlsl_node(&ins->src[1], ctx, byte_offset, VKD3DSP_WRITEMASK_ALL);
+ }
+ else if (multisampled)
{
if (sample_index->type == HLSL_IR_CONSTANT)
vsir_src_from_hlsl_constant_value(&ins->src[2], ctx,
@@ -12093,16 +12359,15 @@ static void sm4_generate_vsir_add_function(struct hlsl_ctx *ctx, struct list *se
struct hlsl_block block = {0};
struct hlsl_scope *scope;
struct hlsl_ir_var *var;
- uint32_t temp_count;
ctx->is_patch_constant_func = func == ctx->patch_constant_func;
compute_liveness(ctx, body);
mark_indexable_vars(ctx, body);
- temp_count = allocate_temp_registers(ctx, body, semantic_vars);
+ allocate_temp_registers(ctx, body, semantic_vars);
if (ctx->result)
return;
- program->temp_count = max(program->temp_count, temp_count);
+ program->temp_count = max(program->temp_count, ctx->temp_count);
hlsl_block_init(&block);
@@ -12113,8 +12378,8 @@ static void sm4_generate_vsir_add_function(struct hlsl_ctx *ctx, struct list *se
sm4_generate_vsir_instr_dcl_semantic(ctx, program, var, &block, &var->loc);
}
- if (temp_count)
- sm4_generate_vsir_instr_dcl_temps(ctx, program, temp_count, &block, &func->loc);
+ if (ctx->temp_count)
+ sm4_generate_vsir_instr_dcl_temps(ctx, program, ctx->temp_count, &block, &func->loc);
LIST_FOR_EACH_ENTRY(scope, &ctx->scopes, struct hlsl_scope, entry)
{
@@ -12427,7 +12692,7 @@ static void sm4_generate_vsir_add_dcl_constant_buffer(struct hlsl_ctx *ctx,
return;
}
- ins->declaration.cb.size = cbuffer->size;
+ ins->declaration.cb.size = align(cbuffer->size, 4) * sizeof(float);
src_param = &ins->declaration.cb.src;
vsir_src_param_init(src_param, VKD3DSPR_CONSTBUFFER, VSIR_DATA_F32, 0);
@@ -12592,6 +12857,9 @@ static void sm4_generate_vsir_add_dcl_texture(struct hlsl_ctx *ctx,
{
switch (component_type->sampler_dim)
{
+ case HLSL_SAMPLER_DIM_STRUCTURED_BUFFER:
+ opcode = VSIR_OP_DCL_RESOURCE_STRUCTURED;
+ break;
case HLSL_SAMPLER_DIM_RAW_BUFFER:
opcode = VSIR_OP_DCL_RESOURCE_RAW;
break;
@@ -12647,7 +12915,7 @@ static void sm4_generate_vsir_add_dcl_texture(struct hlsl_ctx *ctx,
else if (component_type->sampler_dim == HLSL_SAMPLER_DIM_STRUCTURED_BUFFER)
{
ins->structured = true;
- ins->resource_stride = 4 * component_type->e.resource.format->reg_size[HLSL_REGSET_NUMERIC];
+ ins->resource_stride = hlsl_type_get_packed_size(component_type->e.resource.format);
ins->declaration.structured_resource.byte_stride = ins->resource_stride;
}
else
@@ -12784,6 +13052,7 @@ static void sm4_generate_vsir(struct hlsl_ctx *ctx,
}
program->ssa_count = 0;
+ program->temp_count = 0;
if (version->type == VKD3D_SHADER_TYPE_HULL)
generate_vsir_add_program_instruction(ctx, program,
@@ -12801,6 +13070,7 @@ static void sm4_generate_vsir(struct hlsl_ctx *ctx,
generate_vsir_scan_global_flags(ctx, program, semantic_vars, func);
program->ssa_count = ctx->ssa_count;
+ program->temp_count = ctx->temp_count;
}
/* For some reason, for matrices, values from default value initializers end
@@ -12915,14 +13185,16 @@ static enum D3D_RESOURCE_RETURN_TYPE sm4_data_type(const struct hlsl_type *type)
static D3D_SHADER_INPUT_TYPE sm4_resource_type(const struct hlsl_type *type)
{
+ bool structured = type->sampler_dim == HLSL_SAMPLER_DIM_STRUCTURED_BUFFER;
+
switch (type->class)
{
case HLSL_CLASS_SAMPLER:
return D3D_SIT_SAMPLER;
case HLSL_CLASS_TEXTURE:
- return D3D_SIT_TEXTURE;
+ return structured ? D3D_SIT_STRUCTURED : D3D_SIT_TEXTURE;
case HLSL_CLASS_UAV:
- return D3D_SIT_UAV_RWTYPED;
+ return structured ? D3D_SIT_UAV_RWSTRUCTURED : D3D_SIT_UAV_RWTYPED;
default:
break;
}
@@ -12998,7 +13270,8 @@ static D3D_SHADER_VARIABLE_TYPE sm4_base_type(const struct hlsl_type *type)
vkd3d_unreachable();
}
-static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *buffer, struct hlsl_type *type)
+static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *buffer,
+ struct hlsl_type *type, bool structured)
{
const struct hlsl_type *array_type = hlsl_get_multiarray_element_type(type);
const char *name = array_type->name ? array_type->name : "<unnamed>";
@@ -13007,7 +13280,10 @@ static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *b
size_t name_offset = 0;
size_t i;
- if (type->bytecode_offset)
+ if (!structured && type->bytecode_offset)
+ return;
+
+ if (structured && type->packed_bytecode_offset)
return;
if (profile->major_version >= 5)
@@ -13029,7 +13305,7 @@ static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *b
continue;
field->name_bytecode_offset = put_string(buffer, field->name);
- write_sm4_type(ctx, buffer, field->type);
+ write_sm4_type(ctx, buffer, field->type, structured);
++field_count;
}
@@ -13038,15 +13314,29 @@ static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *b
for (i = 0; i < array_type->e.record.field_count; ++i)
{
struct hlsl_struct_field *field = &array_type->e.record.fields[i];
+ unsigned int field_type_offset, offset;
if (!field->type->reg_size[HLSL_REGSET_NUMERIC])
continue;
put_u32(buffer, field->name_bytecode_offset);
- put_u32(buffer, field->type->bytecode_offset);
- put_u32(buffer, field->reg_offset[HLSL_REGSET_NUMERIC] * sizeof(float));
+
+ if (!structured)
+ field_type_offset = field->type->bytecode_offset;
+ else
+ field_type_offset = field->type->packed_bytecode_offset;
+ put_u32(buffer, field_type_offset);
+
+ if (!structured)
+ offset = field->reg_offset[HLSL_REGSET_NUMERIC] * sizeof(float);
+ else
+ offset = struct_field_get_packed_offset(array_type, i);
+ put_u32(buffer, offset);
}
- type->bytecode_offset = put_u32(buffer, vkd3d_make_u32(D3D_SVC_STRUCT, D3D_SVT_VOID));
+ if (!structured)
+ type->bytecode_offset = put_u32(buffer, vkd3d_make_u32(D3D_SVC_STRUCT, D3D_SVT_VOID));
+ else
+ type->packed_bytecode_offset = put_u32(buffer, vkd3d_make_u32(D3D_SVC_STRUCT, D3D_SVT_VOID));
put_u32(buffer, vkd3d_make_u32(1, hlsl_type_component_count(array_type)));
put_u32(buffer, vkd3d_make_u32(array_size, field_count));
put_u32(buffer, fields_offset);
@@ -13054,7 +13344,11 @@ static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *b
else
{
VKD3D_ASSERT(array_type->class <= HLSL_CLASS_LAST_NUMERIC);
- type->bytecode_offset = put_u32(buffer, vkd3d_make_u32(sm4_class(array_type), sm4_base_type(array_type)));
+ if (!structured)
+ type->bytecode_offset = put_u32(buffer, vkd3d_make_u32(sm4_class(array_type), sm4_base_type(array_type)));
+ else
+ type->packed_bytecode_offset = put_u32(buffer,
+ vkd3d_make_u32(sm4_class(array_type), sm4_base_type(array_type)));
put_u32(buffer, vkd3d_make_u32(array_type->e.numeric.dimy, array_type->e.numeric.dimx));
put_u32(buffer, vkd3d_make_u32(array_size, 0));
put_u32(buffer, 1);
@@ -13073,9 +13367,9 @@ static void write_sm4_type(struct hlsl_ctx *ctx, struct vkd3d_bytecode_buffer *b
static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rdef)
{
uint32_t binding_desc_size = (hlsl_version_ge(ctx, 5, 1) ? 10 : 8) * sizeof(uint32_t);
- size_t cbuffers_offset, resources_offset, creator_offset, string_offset;
- unsigned int cbuffer_count = 0, extern_resources_count, i, j;
+ size_t buffers_offset, resources_offset, creator_offset, string_offset;
size_t cbuffer_position, resource_position, creator_position;
+ unsigned int buffer_count = 0, extern_resources_count, i, j;
const struct hlsl_profile_info *profile = ctx->profile;
struct vkd3d_bytecode_buffer buffer = {0};
struct extern_resource *extern_resources;
@@ -13097,10 +13391,20 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
LIST_FOR_EACH_ENTRY(cbuffer, &ctx->buffers, struct hlsl_buffer, entry)
{
if (cbuffer->reg.allocated)
- ++cbuffer_count;
+ ++buffer_count;
+ }
+
+ for (i = 0; i < extern_resources_count; ++i)
+ {
+ const struct extern_resource *resource = &extern_resources[i];
+
+ if (resource->buffer || resource->component_type->sampler_dim != HLSL_SAMPLER_DIM_STRUCTURED_BUFFER)
+ continue;
+
+ ++buffer_count;
}
- put_u32(&buffer, cbuffer_count);
+ put_u32(&buffer, buffer_count);
cbuffer_position = put_u32(&buffer, 0);
put_u32(&buffer, extern_resources_count);
resource_position = put_u32(&buffer, 0);
@@ -13141,12 +13445,19 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
put_u32(&buffer, sm4_resource_type(resource->component_type));
if (resource->regset == HLSL_REGSET_TEXTURES || resource->regset == HLSL_REGSET_UAVS)
{
+ bool structured = resource->component_type->sampler_dim == HLSL_SAMPLER_DIM_STRUCTURED_BUFFER;
unsigned int dimx = resource->component_type->e.resource.format->e.numeric.dimx;
put_u32(&buffer, sm4_data_type(resource->component_type));
put_u32(&buffer, sm4_rdef_resource_dimension(resource->component_type));
- put_u32(&buffer, ~0u); /* FIXME: multisample count */
- flags |= (dimx - 1) << VKD3D_SM4_SIF_TEXTURE_COMPONENTS_SHIFT;
+
+ if (structured)
+ put_u32(&buffer, hlsl_type_get_packed_size(resource->component_type->e.resource.format));
+ else
+ put_u32(&buffer, ~0u); /* FIXME: multisample count */
+
+ if (!structured)
+ flags |= (dimx - 1) << VKD3D_SM4_SIF_TEXTURE_COMPONENTS_SHIFT;
}
else
{
@@ -13175,8 +13486,8 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
/* Buffers. */
- cbuffers_offset = bytecode_align(&buffer);
- set_u32(&buffer, cbuffer_position, cbuffers_offset);
+ buffers_offset = bytecode_align(&buffer);
+ set_u32(&buffer, cbuffer_position, buffers_offset);
LIST_FOR_EACH_ENTRY(cbuffer, &ctx->buffers, struct hlsl_buffer, entry)
{
unsigned int var_count = 0;
@@ -13198,6 +13509,24 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
put_u32(&buffer, cbuffer->type == HLSL_BUFFER_CONSTANT ? D3D_CT_CBUFFER : D3D_CT_TBUFFER);
}
+ for (i = 0; i < extern_resources_count; ++i)
+ {
+ const struct extern_resource *resource = &extern_resources[i];
+ struct hlsl_type *resource_type;
+
+ if (resource->buffer || resource->component_type->sampler_dim != HLSL_SAMPLER_DIM_STRUCTURED_BUFFER)
+ continue;
+
+ resource_type = resource->component_type->e.resource.format;
+
+ put_u32(&buffer, 0); /* name */
+ put_u32(&buffer, 1); /* var count */
+ put_u32(&buffer, 0); /* variable offset */
+ put_u32(&buffer, hlsl_type_get_packed_size(resource_type)); /* size */
+ put_u32(&buffer, 0); /* FIXME: flags */
+ put_u32(&buffer, D3D_CT_RESOURCE_BIND_INFO);
+ }
+
i = 0;
LIST_FOR_EACH_ENTRY(cbuffer, &ctx->buffers, struct hlsl_buffer, entry)
{
@@ -13205,7 +13534,18 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
continue;
string_offset = put_string(&buffer, cbuffer->name);
- set_u32(&buffer, cbuffers_offset + i++ * 6 * sizeof(uint32_t), string_offset);
+ set_u32(&buffer, buffers_offset + i++ * 6 * sizeof(uint32_t), string_offset);
+ }
+
+ for (j = 0; j < extern_resources_count; ++j)
+ {
+ const struct extern_resource *resource = &extern_resources[j];
+
+ if (resource->buffer || resource->component_type->sampler_dim != HLSL_SAMPLER_DIM_STRUCTURED_BUFFER)
+ continue;
+
+ string_offset = put_string(&buffer, resource->name);
+ set_u32(&buffer, buffers_offset + i++ * 6 * sizeof(uint32_t), string_offset);
}
i = 0;
@@ -13216,7 +13556,7 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
if (!cbuffer->reg.allocated)
continue;
- set_u32(&buffer, cbuffers_offset + (i++ * 6 + 2) * sizeof(uint32_t), vars_start);
+ set_u32(&buffer, buffers_offset + (i++ * 6 + 2) * sizeof(uint32_t), vars_start);
LIST_FOR_EACH_ENTRY(var, &ctx->extern_vars, struct hlsl_ir_var, extern_entry)
{
@@ -13255,7 +13595,7 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
string_offset = put_string(&buffer, var->name);
set_u32(&buffer, var_offset, string_offset);
- write_sm4_type(ctx, &buffer, var->data_type);
+ write_sm4_type(ctx, &buffer, var->data_type, false);
set_u32(&buffer, var_offset + 4 * sizeof(uint32_t), var->data_type->bytecode_offset);
if (var->default_values)
@@ -13298,6 +13638,42 @@ static void sm4_generate_rdef(struct hlsl_ctx *ctx, struct vkd3d_shader_code *rd
}
}
+ for (j = 0; j < extern_resources_count; ++j)
+ {
+ const struct extern_resource *resource = &extern_resources[j];
+ struct hlsl_type *resource_type;
+ size_t vars_start;
+
+ if (resource->buffer || resource->component_type->sampler_dim != HLSL_SAMPLER_DIM_STRUCTURED_BUFFER)
+ continue;
+
+ resource_type = resource->component_type->e.resource.format;
+
+ vars_start = bytecode_align(&buffer);
+
+ set_u32(&buffer, buffers_offset + (i++ * 6 + 2) * sizeof(uint32_t), vars_start);
+
+ put_u32(&buffer, 0); /* name */
+ put_u32(&buffer, 0); /* offset */
+ put_u32(&buffer, hlsl_type_get_packed_size(resource_type));
+ put_u32(&buffer, D3D_SVF_USED);
+ put_u32(&buffer, 0); /* type */
+ put_u32(&buffer, 0); /* default value */
+
+ if (profile->major_version >= 5)
+ {
+ put_u32(&buffer, ~0u); /* texture start */
+ put_u32(&buffer, 0); /* texture count */
+ put_u32(&buffer, ~0u); /* sampler start */
+ put_u32(&buffer, 0); /* sampler count */
+ }
+
+ string_offset = put_string(&buffer, "$Element");
+ set_u32(&buffer, vars_start, string_offset);
+ write_sm4_type(ctx, &buffer, resource_type, true);
+ set_u32(&buffer, vars_start + 4 * sizeof(uint32_t), resource_type->packed_bytecode_offset);
+ }
+
creator_offset = put_string(&buffer, vkd3d_shader_get_version(NULL, NULL));
set_u32(&buffer, creator_position, creator_offset);
diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl_constant_ops.c b/libs/vkd3d/libs/vkd3d-shader/hlsl_constant_ops.c
index d339a06e6c7..252ed51a4e4 100644
--- a/libs/vkd3d/libs/vkd3d-shader/hlsl_constant_ops.c
+++ b/libs/vkd3d/libs/vkd3d-shader/hlsl_constant_ops.c
@@ -250,6 +250,36 @@ static bool fold_ceil(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst,
return true;
}
+static bool fold_cos(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst,
+ const struct hlsl_type *dst_type, const struct hlsl_ir_constant *src)
+{
+ enum hlsl_base_type type = dst_type->e.numeric.type;
+ unsigned int k;
+
+ VKD3D_ASSERT(type == src->node.data_type->e.numeric.type);
+
+ for (k = 0; k < dst_type->e.numeric.dimx; ++k)
+ {
+ switch (type)
+ {
+ case HLSL_TYPE_FLOAT:
+ case HLSL_TYPE_HALF:
+ dst->u[k].f = cosf(src->value.u[k].f);
+ break;
+
+ case HLSL_TYPE_DOUBLE:
+ dst->u[k].d = cos(src->value.u[k].d);
+ break;
+
+ default:
+ FIXME("Fold 'cos' for type %s.\n", debug_hlsl_type(ctx, dst_type));
+ return false;
+ }
+ }
+
+ return true;
+}
+
static bool fold_exp2(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst,
const struct hlsl_type *dst_type, const struct hlsl_ir_constant *src)
{
@@ -478,6 +508,48 @@ static bool fold_rcp(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, cons
return true;
}
+static bool fold_reinterpret(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst,
+ const struct hlsl_type *dst_type, const struct hlsl_ir_constant *src)
+{
+ unsigned int k;
+
+ for (k = 0; k < dst_type->e.numeric.dimx; ++k)
+ {
+ dst->u[k] = src->value.u[k];
+ }
+
+ return true;
+}
+
+static bool fold_round(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst,
+ const struct hlsl_type *dst_type, const struct hlsl_ir_constant *src)
+{
+ enum hlsl_base_type type = dst_type->e.numeric.type;
+ unsigned int k;
+
+ VKD3D_ASSERT(type == src->node.data_type->e.numeric.type);
+
+ for (k = 0; k < dst_type->e.numeric.dimx; ++k)
+ {
+ switch (type)
+ {
+ case HLSL_TYPE_FLOAT:
+ case HLSL_TYPE_HALF:
+ /* Somewhat unfortunately, constant folded round() rounds
+ * halfway cases towards positive infinity, as opposed to
+ * nearest even like vsir/TPF round_ne. */
+ dst->u[k].f = floorf(src->value.u[k].f + 0.5f);
+ break;
+
+ default:
+ FIXME("Fold 'round' for type %s.\n", debug_hlsl_type(ctx, dst_type));
+ return false;
+ }
+ }
+
+ return true;
+}
+
static bool fold_rsq(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, const struct hlsl_type *dst_type,
const struct hlsl_ir_constant *src, const struct vkd3d_shader_location *loc)
{
@@ -544,6 +616,36 @@ static bool fold_sat(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, cons
return true;
}
+static bool fold_sin(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst,
+ const struct hlsl_type *dst_type, const struct hlsl_ir_constant *src)
+{
+ enum hlsl_base_type type = dst_type->e.numeric.type;
+ unsigned int k;
+
+ VKD3D_ASSERT(type == src->node.data_type->e.numeric.type);
+
+ for (k = 0; k < dst_type->e.numeric.dimx; ++k)
+ {
+ switch (type)
+ {
+ case HLSL_TYPE_FLOAT:
+ case HLSL_TYPE_HALF:
+ dst->u[k].f = sinf(src->value.u[k].f);
+ break;
+
+ case HLSL_TYPE_DOUBLE:
+ dst->u[k].d = sin(src->value.u[k].d);
+ break;
+
+ default:
+ FIXME("Fold 'sin' for type %s.\n", debug_hlsl_type(ctx, dst_type));
+ return false;
+ }
+ }
+
+ return true;
+}
+
static bool fold_sqrt(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, const struct hlsl_type *dst_type,
const struct hlsl_ir_constant *src, const struct vkd3d_shader_location *loc)
{
@@ -974,6 +1076,44 @@ static bool fold_lshift(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, c
return true;
}
+static bool fold_mad(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, const struct hlsl_type *dst_type,
+ const struct hlsl_ir_constant *src1, const struct hlsl_ir_constant *src2, const struct hlsl_ir_constant *src3)
+{
+ enum hlsl_base_type type = dst_type->e.numeric.type;
+ unsigned int k;
+
+ VKD3D_ASSERT(type == src1->node.data_type->e.numeric.type);
+ VKD3D_ASSERT(type == src2->node.data_type->e.numeric.type);
+ VKD3D_ASSERT(type == src3->node.data_type->e.numeric.type);
+
+ for (k = 0; k < dst_type->e.numeric.dimx; ++k)
+ {
+ switch (type)
+ {
+ case HLSL_TYPE_FLOAT:
+ case HLSL_TYPE_HALF:
+ dst->u[k].f = fmaf(src1->value.u[k].f, src2->value.u[k].f, src3->value.u[k].f);
+ break;
+
+ case HLSL_TYPE_DOUBLE:
+ dst->u[k].d = fma(src1->value.u[k].d, src2->value.u[k].d, src3->value.u[k].d);
+ break;
+
+ case HLSL_TYPE_INT:
+ case HLSL_TYPE_MIN16UINT:
+ case HLSL_TYPE_UINT:
+ dst->u[k].u = src1->value.u[k].u * src2->value.u[k].u + src3->value.u[k].u;
+ break;
+
+ default:
+ FIXME("Fold 'mad' for type %s.\n", debug_hlsl_type(ctx, dst_type));
+ return false;
+ }
+ }
+
+ return true;
+}
+
static bool fold_max(struct hlsl_ctx *ctx, struct hlsl_constant_value *dst, const struct hlsl_type *dst_type,
const struct hlsl_ir_constant *src1, const struct hlsl_ir_constant *src2)
{
@@ -1263,6 +1403,10 @@ bool hlsl_fold_constant_exprs(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr,
success = fold_ceil(ctx, &res, instr->data_type, arg1);
break;
+ case HLSL_OP1_COS:
+ success = fold_cos(ctx, &res, instr->data_type, arg1);
+ break;
+
case HLSL_OP1_EXP2:
success = fold_exp2(ctx, &res, instr->data_type, arg1);
break;
@@ -1291,6 +1435,14 @@ bool hlsl_fold_constant_exprs(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr,
success = fold_rcp(ctx, &res, instr->data_type, arg1, &instr->loc);
break;
+ case HLSL_OP1_REINTERPRET:
+ success = fold_reinterpret(ctx, &res, instr->data_type, arg1);
+ break;
+
+ case HLSL_OP1_ROUND:
+ success = fold_round(ctx, &res, instr->data_type, arg1);
+ break;
+
case HLSL_OP1_RSQ:
success = fold_rsq(ctx, &res, instr->data_type, arg1, &instr->loc);
break;
@@ -1299,6 +1451,10 @@ bool hlsl_fold_constant_exprs(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr,
success = fold_sat(ctx, &res, instr->data_type, arg1);
break;
+ case HLSL_OP1_SIN:
+ success = fold_sin(ctx, &res, instr->data_type, arg1);
+ break;
+
case HLSL_OP1_SQRT:
success = fold_sqrt(ctx, &res, instr->data_type, arg1, &instr->loc);
break;
@@ -1373,6 +1529,10 @@ bool hlsl_fold_constant_exprs(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr,
success = fold_dp2add(ctx, &res, instr->data_type, arg1, arg2, arg3);
break;
+ case HLSL_OP3_MAD:
+ success = fold_mad(ctx, &res, instr->data_type, arg1, arg2, arg3);
+ break;
+
case HLSL_OP3_TERNARY:
success = fold_ternary(ctx, &res, instr->data_type, arg1, arg2, arg3);
break;
@@ -1393,74 +1553,6 @@ bool hlsl_fold_constant_exprs(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr,
return success;
}
-static bool constant_is_zero(struct hlsl_ir_constant *const_arg)
-{
- struct hlsl_type *data_type = const_arg->node.data_type;
- unsigned int k;
-
- for (k = 0; k < data_type->e.numeric.dimx; ++k)
- {
- switch (data_type->e.numeric.type)
- {
- case HLSL_TYPE_FLOAT:
- case HLSL_TYPE_HALF:
- if (const_arg->value.u[k].f != 0.0f)
- return false;
- break;
-
- case HLSL_TYPE_DOUBLE:
- if (const_arg->value.u[k].d != 0.0)
- return false;
- break;
-
- case HLSL_TYPE_UINT:
- case HLSL_TYPE_INT:
- case HLSL_TYPE_BOOL:
- case HLSL_TYPE_MIN16UINT:
- if (const_arg->value.u[k].u != 0)
- return false;
- break;
- }
- }
- return true;
-}
-
-static bool constant_is_one(struct hlsl_ir_constant *const_arg)
-{
- struct hlsl_type *data_type = const_arg->node.data_type;
- unsigned int k;
-
- for (k = 0; k < data_type->e.numeric.dimx; ++k)
- {
- switch (data_type->e.numeric.type)
- {
- case HLSL_TYPE_FLOAT:
- case HLSL_TYPE_HALF:
- if (const_arg->value.u[k].f != 1.0f)
- return false;
- break;
-
- case HLSL_TYPE_DOUBLE:
- if (const_arg->value.u[k].d != 1.0)
- return false;
- break;
-
- case HLSL_TYPE_UINT:
- case HLSL_TYPE_INT:
- case HLSL_TYPE_MIN16UINT:
- if (const_arg->value.u[k].u != 1)
- return false;
- break;
-
- case HLSL_TYPE_BOOL:
- if (const_arg->value.u[k].u != ~0)
- return false;
- break;
- }
- }
- return true;
-}
-
bool hlsl_fold_constant_identities(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr, void *context)
{
struct hlsl_ir_constant *const_arg = NULL;
@@ -1502,26 +1594,26 @@ bool hlsl_fold_constant_identities(struct hlsl_ctx *ctx, struct hlsl_ir_node *in
switch (expr->op)
{
case HLSL_OP2_ADD:
- if (constant_is_zero(const_arg))
+ if (hlsl_constant_is_zero(const_arg))
res_node = mut_arg;
break;
case HLSL_OP2_MUL:
- if (constant_is_one(const_arg))
+ if (hlsl_constant_is_one(const_arg))
res_node = mut_arg;
break;
case HLSL_OP2_LOGIC_AND:
- if (constant_is_zero(const_arg))
+ if (hlsl_constant_is_zero(const_arg))
res_node = &const_arg->node;
- else if (constant_is_one(const_arg))
+ else if (hlsl_constant_is_one(const_arg))
res_node = mut_arg;
break;
case HLSL_OP2_LOGIC_OR:
- if (constant_is_zero(const_arg))
+ if (hlsl_constant_is_zero(const_arg))
res_node = mut_arg;
- else if (constant_is_one(const_arg))
+ else if (hlsl_constant_is_one(const_arg))
res_node = &const_arg->node;
break;
@@ -1649,6 +1741,9 @@ bool hlsl_normalize_binary_exprs(struct hlsl_ctx *ctx, struct hlsl_ir_node *inst
if (instr->data_type->class > HLSL_CLASS_VECTOR)
return false;
+ if (expr->operands[2].node)
+ return false;
+
hlsl_block_init(&block);
arg1 = expr->operands[0].node;
diff --git a/libs/vkd3d/libs/vkd3d-shader/ir.c b/libs/vkd3d/libs/vkd3d-shader/ir.c
index 23e059a3490..29bf62709eb 100644
--- a/libs/vkd3d/libs/vkd3d-shader/ir.c
+++ b/libs/vkd3d/libs/vkd3d-shader/ir.c
@@ -27,8 +27,53 @@ struct vsir_transformation_context
uint64_t config_flags;
const struct vkd3d_shader_compile_info *compile_info;
struct vkd3d_shader_message_context *message_context;
+ struct vkd3d_shader_location null_location;
};
+static void vsir_transformation_context_init(struct vsir_transformation_context *ctx,
+ struct vsir_program *program, uint64_t config_flags, const struct vkd3d_shader_compile_info *compile_info,
+ struct vkd3d_shader_message_context *message_context)
+{
+ *ctx = (struct vsir_transformation_context)
+ {
+ .result = VKD3D_OK,
+ .program = program,
+ .config_flags = config_flags,
+ .compile_info = compile_info,
+ .message_context = message_context,
+ .null_location = {.source_name = compile_info->source_name},
+ };
+};
+
+const char *vsir_data_type_get_name(enum vsir_data_type t, const char *error)
+{
+ static const char * const names[] =
+ {
+ [VSIR_DATA_BOOL ] = "bool",
+ [VSIR_DATA_F16 ] = "half",
+ [VSIR_DATA_F32 ] = "float",
+ [VSIR_DATA_F64 ] = "double",
+ [VSIR_DATA_I16 ] = "i16",
+ [VSIR_DATA_I32 ] = "int",
+ [VSIR_DATA_I64 ] = "i64",
+ [VSIR_DATA_U8 ] = "uint8",
+ [VSIR_DATA_U16 ] = "uint16",
+ [VSIR_DATA_U32 ] = "uint",
+ [VSIR_DATA_U64 ] = "uint64",
+ [VSIR_DATA_SNORM ] = "snorm",
+ [VSIR_DATA_UNORM ] = "unorm",
+ [VSIR_DATA_OPAQUE ] = "opaque",
+ [VSIR_DATA_MIXED ] = "mixed",
+ [VSIR_DATA_CONTINUED] = "<continued>",
+ [VSIR_DATA_UNUSED ] = "<unused>",
+ };
+
+ if ((size_t)t < ARRAY_SIZE(names))
+ return names[t] ? names[t] : error;
+
+ return error;
+}
+
const char *vsir_opcode_get_name(enum vkd3d_shader_opcode op, const char *error)
{
static const char * const names[] =
@@ -373,6 +418,183 @@ const char *vsir_opcode_get_name(enum vkd3d_shader_opcode op, const char *error)
return error;
}
+static struct vkd3d_shader_param_node *shader_param_allocator_node_create(
+ struct vkd3d_shader_param_allocator *allocator)
+{
+ struct vkd3d_shader_param_node *node;
+
+ if (!(node = vkd3d_malloc(offsetof(struct vkd3d_shader_param_node, param[allocator->count * allocator->stride]))))
+ return NULL;
+ node->next = NULL;
+
+ return node;
+}
+
+static void shader_param_allocator_init(struct vkd3d_shader_param_allocator *allocator, size_t count, size_t stride)
+{
+ allocator->count = max(count, MAX_REG_OUTPUT);
+ allocator->stride = stride;
+ allocator->head = NULL;
+ allocator->current = NULL;
+ allocator->index = allocator->count;
+}
+
+static void shader_param_allocator_destroy(struct vkd3d_shader_param_allocator *allocator)
+{
+ struct vkd3d_shader_param_node *current = allocator->head;
+
+ while (current)
+ {
+ struct vkd3d_shader_param_node *next = current->next;
+ vkd3d_free(current);
+ current = next;
+ }
+}
+
+void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, size_t count)
+{
+ void *params;
+
+ if (!allocator->current || count > allocator->count - allocator->index)
+ {
+ struct vkd3d_shader_param_node *next;
+
+ allocator->count = max(allocator->count, count);
+ if (!(next = shader_param_allocator_node_create(allocator)))
+ return NULL;
+ if (allocator->current)
+ allocator->current->next = next;
+ else
+ allocator->head = next;
+ allocator->current = next;
+ allocator->index = 0;
+ }
+
+ params = &allocator->current->param[allocator->index * allocator->stride];
+ allocator->index += count;
+
+ return params;
+}
+
+bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *array, size_t reserve)
+{
+ if (!vkd3d_array_reserve((void **)&array->elements, &array->capacity, reserve, sizeof(*array->elements)))
+ {
+ ERR("Failed to allocate instructions.\n");
+ return false;
+ }
+
+ return true;
+}
+
+bool shader_instruction_array_insert_at(struct vkd3d_shader_instruction_array *array, size_t idx, size_t count)
+{
+ VKD3D_ASSERT(idx <= array->count);
+
+ if (!shader_instruction_array_reserve(array, array->count + count))
+ return false;
+
+ memmove(&array->elements[idx + count], &array->elements[idx], (array->count - idx) * sizeof(*array->elements));
+ memset(&array->elements[idx], 0, count * sizeof(*array->elements));
+ array->count += count;
+
+ return true;
+}
+
+bool shader_instruction_array_add_icb(struct vkd3d_shader_instruction_array *array,
+ struct vkd3d_shader_immediate_constant_buffer *icb)
+{
+ if (!vkd3d_array_reserve((void **)&array->icbs, &array->icb_capacity, array->icb_count + 1, sizeof(*array->icbs)))
+ return false;
+
+ array->icbs[array->icb_count++] = icb;
+
+ return true;
+}
+
+static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
+ struct vkd3d_shader_instruction_array *array, const struct vkd3d_shader_src_param *params, size_t count);
+
+static bool shader_register_clone_relative_addresses(struct vkd3d_shader_register *reg,
+ struct vkd3d_shader_instruction_array *array)
+{
+ size_t i;
+
+ for (i = 0; i < reg->idx_count; ++i)
+ {
+ if (!reg->idx[i].rel_addr)
+ continue;
+
+ if (!(reg->idx[i].rel_addr = shader_instruction_array_clone_src_params(array, reg->idx[i].rel_addr, 1)))
+ return false;
+ }
+
+ return true;
+}
+
+static struct vkd3d_shader_dst_param *shader_instruction_array_clone_dst_params(
+ struct vkd3d_shader_instruction_array *array, const struct vkd3d_shader_dst_param *params, size_t count)
+{
+ struct vkd3d_shader_dst_param *dst_params;
+ size_t i;
+
+ if (!(dst_params = shader_dst_param_allocator_get(&array->dst_params, count)))
+ return NULL;
+
+ memcpy(dst_params, params, count * sizeof(*params));
+ for (i = 0; i < count; ++i)
+ {
+ if (!shader_register_clone_relative_addresses(&dst_params[i].reg, array))
+ return NULL;
+ }
+
+ return dst_params;
+}
+
+static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
+ struct vkd3d_shader_instruction_array *array, const struct vkd3d_shader_src_param *params, size_t count)
+{
+ struct vkd3d_shader_src_param *src_params;
+ size_t i;
+
+ if (!(src_params = shader_src_param_allocator_get(&array->src_params, count)))
+ return NULL;
+
+ memcpy(src_params, params, count * sizeof(*params));
+ for (i = 0; i < count; ++i)
+ {
+ if (!shader_register_clone_relative_addresses(&src_params[i].reg, array))
+ return NULL;
+ }
+
+ return src_params;
+}
+
+static void shader_instruction_array_destroy(struct vkd3d_shader_instruction_array *array)
+{
+ unsigned int i;
+
+ vkd3d_free(array->elements);
+ shader_param_allocator_destroy(&array->dst_params);
+ shader_param_allocator_destroy(&array->src_params);
+ for (i = 0; i < array->icb_count; ++i)
+ {
+ vkd3d_free(array->icbs[i]);
+ }
+ vkd3d_free(array->icbs);
+}
+
+static bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *array, size_t reserve)
+{
+ memset(array, 0, sizeof(*array));
+ /* Size the parameter initial allocations so they are large enough for most shaders. The
+ * code path for chained allocations will be tested if a few shaders need to use it. */
+ shader_param_allocator_init(&array->dst_params, reserve - reserve / 8u, sizeof(struct vkd3d_shader_dst_param));
+ shader_param_allocator_init(&array->src_params, reserve * 2u, sizeof(struct vkd3d_shader_src_param));
+
+ return shader_instruction_array_reserve(array, reserve);
+}
+
static int convert_parameter_info(const struct vkd3d_shader_compile_info *compile_info,
unsigned int *ret_count, const struct vkd3d_shader_parameter1 **ret_parameters)
{
@@ -864,6 +1086,23 @@ static void vkd3d_shader_instruction_make_nop(struct vkd3d_shader_instruction *i
vsir_instruction_init(ins, &location, VSIR_OP_NOP);
}
+/* NOTE: Immediate constant buffers are not cloned, so the source must not be destroyed while the
+ * destination is in use. This seems like a reasonable requirement given how this is currently used. */
+static bool vsir_program_iterator_clone_instruction(struct vsir_program_iterator *dst_it,
+ const struct vkd3d_shader_instruction *src)
+{
+ struct vkd3d_shader_instruction *dst = vsir_program_iterator_current(dst_it);
+
+ *dst = *src;
+
+ if (dst->dst_count && !(dst->dst = shader_instruction_array_clone_dst_params(dst_it->array,
+ dst->dst, dst->dst_count)))
+ return false;
+
+ return !dst->src_count || !!(dst->src = shader_instruction_array_clone_src_params(dst_it->array,
+ dst->src, dst->src_count));
+}
+
static bool get_opcode_from_rel_op(enum vkd3d_shader_rel_op rel_op,
enum vsir_data_type data_type, enum vkd3d_shader_opcode *opcode, bool *requires_swap)
{
@@ -1669,10 +1908,22 @@ static enum vkd3d_result vsir_program_lower_d3dbc_instructions(struct vsir_progr
switch (ins->opcode)
{
+ case VSIR_OP_IFC:
+ ret = vsir_program_lower_ifc(program, &it, &tmp_idx, message_context);
+ break;
+
+ case VSIR_OP_SINCOS:
+ ret = vsir_program_lower_sm1_sincos(program, &it);
+ break;
+
case VSIR_OP_TEXCRD:
ret = vsir_program_lower_texcrd(program, ins, message_context);
break;
+ case VSIR_OP_TEXKILL:
+ ret = vsir_program_lower_texkill(program, &it, &tmp_idx);
+ break;
+
case VSIR_OP_TEXLD:
if (program->shader_version.major == 1)
ret = vsir_program_lower_texld_sm1(program, ins, message_context);
@@ -1682,6 +1933,14 @@ static enum vkd3d_result vsir_program_lower_d3dbc_instructions(struct vsir_progr
ret = vsir_program_lower_texld(program, ins, message_context);
break;
+ case VSIR_OP_TEXLDD:
+ ret = vsir_program_lower_texldd(program, ins);
+ break;
+
+ case VSIR_OP_TEXLDL:
+ ret = vsir_program_lower_texldl(program, ins);
+ break;
+
default:
ret = VKD3D_OK;
break;
@@ -1698,7 +1957,6 @@ static enum vkd3d_result vsir_program_lower_instructions(struct vsir_program *pr
struct vsir_transformation_context *ctx)
{
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
- struct vkd3d_shader_message_context *message_context = ctx->message_context;
struct vkd3d_shader_instruction *ins;
unsigned int tmp_idx = ~0u;
enum vkd3d_result ret;
@@ -1707,16 +1965,6 @@ static enum vkd3d_result vsir_program_lower_instructions(struct vsir_program *pr
{
switch (ins->opcode)
{
- case VSIR_OP_IFC:
- if ((ret = vsir_program_lower_ifc(program, &it, &tmp_idx, message_context)) < 0)
- return ret;
- break;
-
- case VSIR_OP_TEXKILL:
- if ((ret = vsir_program_lower_texkill(program, &it, &tmp_idx)) < 0)
- return ret;
- break;
-
case VSIR_OP_MAD:
if ((ret = vsir_program_lower_precise_mad(program, &it, &tmp_idx)) < 0)
return ret;
@@ -1725,6 +1973,8 @@ static enum vkd3d_result vsir_program_lower_instructions(struct vsir_program *pr
case VSIR_OP_DCL:
case VSIR_OP_DCL_CONSTANT_BUFFER:
case VSIR_OP_DCL_GLOBAL_FLAGS:
+ case VSIR_OP_DCL_INPUT_PRIMITIVE:
+ case VSIR_OP_DCL_OUTPUT_TOPOLOGY:
case VSIR_OP_DCL_SAMPLER:
case VSIR_OP_DCL_TEMPS:
case VSIR_OP_DCL_TESSELLATOR_DOMAIN:
@@ -1765,25 +2015,7 @@ static enum vkd3d_result vsir_program_lower_instructions(struct vsir_program *pr
break;
case VSIR_OP_SINCOS:
- if (ins->dst_count == 1)
- {
- if ((ret = vsir_program_lower_sm1_sincos(program, &it)) < 0)
- return ret;
- }
- else
- {
- if ((ret = vsir_program_lower_sm4_sincos(program, &it, ctx)) < 0)
- return ret;
- }
- break;
-
- case VSIR_OP_TEXLDD:
- if ((ret = vsir_program_lower_texldd(program, ins)) < 0)
- return ret;
- break;
-
- case VSIR_OP_TEXLDL:
- if ((ret = vsir_program_lower_texldl(program, ins)) < 0)
+ if ((ret = vsir_program_lower_sm4_sincos(program, &it, ctx)) < 0)
return ret;
break;
@@ -1823,16 +2055,19 @@ static enum vkd3d_result vsir_program_ensure_ret(struct vsir_program *program,
struct vsir_transformation_context *ctx)
{
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
- static const struct vkd3d_shader_location no_loc;
struct vkd3d_shader_instruction *ins;
+ struct vkd3d_shader_location loc;
- ins = vsir_program_iterator_tail(&it);
- if (ins && ins->opcode == VSIR_OP_RET)
+ if (!(ins = vsir_program_iterator_tail(&it)))
+ loc = ctx->null_location;
+ else if (ins->opcode == VSIR_OP_RET)
return VKD3D_OK;
+ else
+ loc = ins->location;
if (!(ins = vsir_program_append(program)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- vsir_instruction_init(ins, &no_loc, VSIR_OP_RET);
+ vsir_instruction_init(ins, &loc, VSIR_OP_RET);
return VKD3D_OK;
}
@@ -1923,7 +2158,7 @@ static enum vkd3d_result vsir_program_ensure_diffuse(struct vsir_program *progra
struct vsir_transformation_context *ctx)
{
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
- static const struct vkd3d_shader_location no_loc;
+ struct vkd3d_shader_location loc = ctx->null_location;
struct vkd3d_shader_instruction *ins;
unsigned int i;
@@ -1937,15 +2172,16 @@ static enum vkd3d_result vsir_program_ensure_diffuse(struct vsir_program *progra
for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
if (!vsir_instruction_is_dcl(ins) && ins->opcode != VSIR_OP_LABEL && ins->opcode != VSIR_OP_NOP)
+ {
+ loc = ins->location;
break;
+ }
}
- vsir_program_iterator_prev(&it);
- if (!vsir_program_iterator_insert_after(&it, 1))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(&it, 1)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(&it);
- vsir_instruction_init_with_params(program, ins, &no_loc, VSIR_OP_MOV, 1, 1);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MOV, 1, 1);
vsir_dst_param_init(&ins->dst[0], VKD3DSPR_ATTROUT, VSIR_DATA_F32, 1);
ins->dst[0].reg.idx[0].offset = 0;
ins->dst[0].reg.dimension = VSIR_DIMENSION_VEC4;
@@ -2162,10 +2398,8 @@ static enum vkd3d_result vsir_program_remap_output_signature(struct vsir_program
continue;
loc = ins->location;
- vsir_program_iterator_prev(&it);
- if (!vsir_program_iterator_insert_after(&it, uninit_varying_count))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(&it, uninit_varying_count)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(&it);
for (unsigned int j = signature->element_count - uninit_varying_count; j < signature->element_count; ++j)
{
@@ -2200,8 +2434,6 @@ struct hull_flattener
{
struct vsir_program *program;
- unsigned int instance_count;
- unsigned int phase_body_idx;
enum vkd3d_shader_opcode phase;
struct vkd3d_shader_location last_ret_location;
unsigned int *ssa_map;
@@ -2213,68 +2445,6 @@ static bool flattener_is_in_fork_or_join_phase(const struct hull_flattener *flat
return flattener->phase == VSIR_OP_HS_FORK_PHASE || flattener->phase == VSIR_OP_HS_JOIN_PHASE;
}
-struct shader_phase_location
-{
- unsigned int index;
- unsigned int instance_count;
- unsigned int instruction_count;
-};
-
-struct shader_phase_location_array
-{
- /* Unlikely worst case: one phase for each component of each output register. */
- struct shader_phase_location locations[MAX_REG_OUTPUT * VKD3D_VEC4_SIZE];
- unsigned int count;
-};
-
-static void flattener_eliminate_phase_related_dcls(struct hull_flattener *normaliser, unsigned int index,
- struct vkd3d_shader_instruction *ins, struct shader_phase_location_array *locations)
-{
- struct shader_phase_location *loc;
- bool b;
-
- if (ins->opcode == VSIR_OP_HS_FORK_PHASE || ins->opcode == VSIR_OP_HS_JOIN_PHASE)
- {
- b = flattener_is_in_fork_or_join_phase(normaliser);
- /* Reset the phase info. */
- normaliser->phase_body_idx = ~0u;
- normaliser->phase = ins->opcode;
- normaliser->instance_count = 1;
- /* Leave the first occurrence and delete the rest. */
- if (b)
- vkd3d_shader_instruction_make_nop(ins);
- return;
- }
- else if (ins->opcode == VSIR_OP_DCL_HS_FORK_PHASE_INSTANCE_COUNT
- || ins->opcode == VSIR_OP_DCL_HS_JOIN_PHASE_INSTANCE_COUNT)
- {
- normaliser->instance_count = ins->declaration.count + !ins->declaration.count;
- vkd3d_shader_instruction_make_nop(ins);
- return;
- }
-
- if (normaliser->phase == VSIR_OP_INVALID || vsir_instruction_is_dcl(ins))
- return;
-
- if (normaliser->phase_body_idx == ~0u)
- normaliser->phase_body_idx = index;
-
- if (ins->opcode == VSIR_OP_RET)
- {
- normaliser->last_ret_location = ins->location;
- vkd3d_shader_instruction_make_nop(ins);
- if (locations->count >= ARRAY_SIZE(locations->locations))
- {
- FIXME("Insufficient space for phase location.\n");
- return;
- }
- loc = &locations->locations[locations->count++];
- loc->index = normaliser->phase_body_idx;
- loc->instance_count = normaliser->instance_count;
- loc->instruction_count = index - normaliser->phase_body_idx;
- }
-}
-
static void flattener_fixup_ssa_register(struct hull_flattener *normaliser,
struct vkd3d_shader_register *reg, unsigned int instance_id)
{
@@ -2337,54 +2507,109 @@ static void flattener_fixup_registers(struct hull_flattener *normaliser,
flattener_fixup_register_indices(normaliser, &ins->dst[i].reg, instance_id);
}
-static enum vkd3d_result flattener_flatten_phases(struct hull_flattener *normaliser,
- struct shader_phase_location_array *locations)
+static enum vkd3d_result flattener_replicate_location(struct hull_flattener *normaliser,
+ struct vsir_program_iterator *it, size_t instance_count, size_t instruction_count)
{
- struct vkd3d_shader_instruction_array *instructions = &normaliser->program->instructions;
- struct shader_phase_location *loc;
- unsigned int i, j, k, end, count;
-
- for (i = 0, count = 0; i < locations->count; ++i)
- count += (locations->locations[i].instance_count - 1) * locations->locations[i].instruction_count;
+ struct vsir_program_iterator dst_it, src_it, first_it;
+ struct vkd3d_shader_instruction *ins;
+ unsigned int i, j;
+ size_t count;
- if (!shader_instruction_array_reserve(instructions, instructions->count + count))
+ VKD3D_ASSERT(instance_count);
+ count = (instance_count - 1) * instruction_count;
+ if (!vsir_program_iterator_insert_before(it, &first_it, count))
return VKD3D_ERROR_OUT_OF_MEMORY;
- end = instructions->count;
- instructions->count += count;
- for (i = locations->count; i > 0; --i)
+ /* Make a copy of the non-dcl instructions for each instance. */
+ dst_it = first_it;
+ for (i = 1; i < instance_count; ++i)
{
- loc = &locations->locations[i - 1];
- j = loc->index + loc->instruction_count;
- memmove(&instructions->elements[j + count], &instructions->elements[j],
- (end - j) * sizeof(*instructions->elements));
- end = j;
- count -= (loc->instance_count - 1) * loc->instruction_count;
- loc->index += count;
+ src_it = *it;
+ for (j = 0; j < instruction_count; ++j)
+ {
+ if (!vsir_program_iterator_clone_instruction(&dst_it, vsir_program_iterator_current(&src_it)))
+ return VKD3D_ERROR_OUT_OF_MEMORY;
+
+ vsir_program_iterator_next(&dst_it);
+ vsir_program_iterator_next(&src_it);
+ }
+ }
+ /* Replace each reference to the instance id with a constant instance id. */
+ *it = first_it;
+ for (i = 0; i < instance_count; ++i)
+ {
+ if (i)
+ memset(normaliser->ssa_map, 0xff, normaliser->orig_ssa_count * sizeof(*normaliser->ssa_map));
+
+ for (j = 0; j < instruction_count; ++j)
+ {
+ ins = vsir_program_iterator_current(it);
+ flattener_fixup_registers(normaliser, ins, i);
+ vsir_program_iterator_next(it);
+ }
}
- for (i = 0, count = 0; i < locations->count; ++i)
+ return VKD3D_OK;
+}
+
+static enum vkd3d_result flattener_flatten_phases(struct hull_flattener *normaliser)
+{
+ struct vsir_program_iterator it = vsir_program_iterator(&normaliser->program->instructions);
+ struct vsir_program_iterator phase_body_it;
+ struct vkd3d_shader_instruction *ins;
+ bool b, phase_body_it_valid = false;
+ unsigned int instruction_count = 0;
+ unsigned int instance_count = 0;
+ enum vkd3d_result res;
+
+ normaliser->phase = VSIR_OP_INVALID;
+ for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
- loc = &locations->locations[i];
- /* Make a copy of the non-dcl instructions for each instance. */
- for (j = 1; j < loc->instance_count; ++j)
+ if (ins->opcode == VSIR_OP_HS_FORK_PHASE || ins->opcode == VSIR_OP_HS_JOIN_PHASE)
{
- for (k = 0; k < loc->instruction_count; ++k)
- {
- if (!shader_instruction_array_clone_instruction(instructions,
- loc->index + loc->instruction_count * j + k, loc->index + k))
- return VKD3D_ERROR_OUT_OF_MEMORY;
- }
+ b = flattener_is_in_fork_or_join_phase(normaliser);
+ /* Reset the phase info. */
+ phase_body_it_valid = false;
+ normaliser->phase = ins->opcode;
+ instance_count = 1;
+ instruction_count = 0;
+ /* Leave the first occurrence and delete the rest. */
+ if (b)
+ vkd3d_shader_instruction_make_nop(ins);
+ continue;
+ }
+ else if (ins->opcode == VSIR_OP_DCL_HS_FORK_PHASE_INSTANCE_COUNT
+ || ins->opcode == VSIR_OP_DCL_HS_JOIN_PHASE_INSTANCE_COUNT)
+ {
+ instance_count = ins->declaration.count + !ins->declaration.count;
+ vkd3d_shader_instruction_make_nop(ins);
+ ++instruction_count;
+ continue;
}
- /* Replace each reference to the instance id with a constant instance id. */
- for (j = 0; j < loc->instance_count; ++j)
+
+ if (normaliser->phase == VSIR_OP_INVALID)
+ continue;
+
+ if (!phase_body_it_valid && !vsir_instruction_is_dcl(ins))
{
- if (j != 0)
- memset(normaliser->ssa_map, 0xff, normaliser->orig_ssa_count * sizeof(*normaliser->ssa_map));
+ phase_body_it_valid = true;
+ phase_body_it = it;
+ instruction_count = 0;
+ }
- for (k = 0; k < loc->instruction_count; ++k)
- flattener_fixup_registers(normaliser,
- &instructions->elements[loc->index + loc->instruction_count * j + k], j);
+ if (ins->opcode == VSIR_OP_RET)
+ {
+ normaliser->last_ret_location = ins->location;
+ vkd3d_shader_instruction_make_nop(ins);
+ it = phase_body_it;
+ if ((res = flattener_replicate_location(normaliser, &it,
+ instance_count, instruction_count)) < 0)
+ return res;
+ phase_body_it_valid = false;
+ }
+ else
+ {
+ ++instruction_count;
}
}
@@ -2394,19 +2619,10 @@ static enum vkd3d_result flattener_flatten_phases(struct hull_flattener *normali
static enum vkd3d_result vsir_program_flatten_hull_shader_phases(struct vsir_program *program,
struct vsir_transformation_context *ctx)
{
- struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
- struct shader_phase_location_array locations;
struct hull_flattener flattener = {program};
struct vkd3d_shader_instruction *ins;
enum vkd3d_result result = VKD3D_OK;
- unsigned int i;
- flattener.phase = VSIR_OP_INVALID;
- locations.count = 0;
- for (ins = vsir_program_iterator_head(&it), i = 0; ins; ins = vsir_program_iterator_next(&it), ++i)
- {
- flattener_eliminate_phase_related_dcls(&flattener, i, ins, &locations);
- }
bitmap_clear(program->io_dcls, VKD3DSPR_FORKINSTID);
bitmap_clear(program->io_dcls, VKD3DSPR_JOININSTID);
@@ -2414,8 +2630,7 @@ static enum vkd3d_result vsir_program_flatten_hull_shader_phases(struct vsir_pro
if (!(flattener.ssa_map = vkd3d_calloc(flattener.orig_ssa_count, sizeof(*flattener.ssa_map))))
return VKD3D_ERROR_OUT_OF_MEMORY;
- result = flattener_flatten_phases(&flattener, &locations);
-
+ result = flattener_flatten_phases(&flattener);
vkd3d_free(flattener.ssa_map);
flattener.ssa_map = NULL;
@@ -2481,8 +2696,8 @@ static void shader_dst_param_normalise_outpointid(struct vkd3d_shader_dst_param
}
static enum vkd3d_result control_point_normaliser_emit_hs_input(struct control_point_normaliser *normaliser,
- const struct shader_signature *s, unsigned int input_control_point_count, unsigned int dst,
- const struct vkd3d_shader_location *location)
+ const struct shader_signature *s, unsigned int input_control_point_count,
+ struct vsir_program_iterator *dst_it, const struct vkd3d_shader_location *location)
{
struct vkd3d_shader_instruction *ins;
const struct signature_element *e;
@@ -2491,17 +2706,11 @@ static enum vkd3d_result control_point_normaliser_emit_hs_input(struct control_p
for (i = 0; i < s->element_count; ++i)
count += !!s->elements[i].used_mask;
- if (!shader_instruction_array_reserve(&normaliser->instructions, normaliser->instructions.count + count))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(dst_it, count)))
return VKD3D_ERROR_OUT_OF_MEMORY;
-
- memmove(&normaliser->instructions.elements[dst + count], &normaliser->instructions.elements[dst],
- (normaliser->instructions.count - dst) * sizeof(*normaliser->instructions.elements));
- normaliser->instructions.count += count;
-
- ins = &normaliser->instructions.elements[dst];
vsir_instruction_init(ins, location, VSIR_OP_HS_CONTROL_POINT_PHASE);
- ++ins;
+ ins = vsir_program_iterator_next(dst_it);
for (i = 0; i < s->element_count; ++i)
{
@@ -2533,7 +2742,7 @@ static enum vkd3d_result control_point_normaliser_emit_hs_input(struct control_p
ins->src[0].reg.idx[0].rel_addr = normaliser->outpointid_param;
ins->src[0].reg.idx[1].offset = e->register_index;
- ++ins;
+ ins = vsir_program_iterator_next(dst_it);
}
vsir_instruction_init(ins, location, VSIR_OP_RET);
@@ -2605,8 +2814,8 @@ static enum vkd3d_result instruction_array_normalise_hull_shader_control_point_i
case VSIR_OP_HS_JOIN_PHASE:
/* ins may be relocated if the instruction array expands. */
location = ins->location;
- ret = control_point_normaliser_emit_hs_input(&normaliser, &program->input_signature,
- input_control_point_count, i, &location);
+ ret = control_point_normaliser_emit_hs_input(&normaliser,
+ &program->input_signature, input_control_point_count, &it, &location);
program->instructions = normaliser.instructions;
program->normalisation_level = VSIR_NORMALISED_HULL_CONTROL_POINT_IO;
return ret;
@@ -4233,9 +4442,11 @@ static enum vkd3d_result vsir_program_lower_switch_to_selection_ladder(struct vs
struct vsir_transformation_context *ctx)
{
unsigned int block_count = program->block_count, ssa_count = program->ssa_count, current_label = 0, if_label;
- size_t ins_capacity = 0, ins_count = 0, i, map_capacity = 0, map_count = 0;
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
+ size_t ins_capacity = 0, ins_count = 0, map_capacity = 0, map_count = 0;
struct vkd3d_shader_instruction *instructions = NULL;
struct lower_switch_to_if_ladder_block_mapping *block_map = NULL;
+ struct vkd3d_shader_instruction *ins;
VKD3D_ASSERT(program->cf_type == VSIR_CF_BLOCKS);
@@ -4245,9 +4456,8 @@ static enum vkd3d_result vsir_program_lower_switch_to_selection_ladder(struct vs
/* First subpass: convert SWITCH_MONOLITHIC instructions to
* selection ladders, keeping a map between blocks before and
* after the subpass. */
- for (i = 0; i < program->instructions.count; ++i)
+ for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
- struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
unsigned int case_count, j, default_label;
switch (ins->opcode)
@@ -4800,8 +5010,8 @@ struct vsir_cfg
{
struct vkd3d_shader_message_context *message_context;
struct vsir_program *program;
- size_t function_begin;
- size_t function_end;
+ struct vsir_program_iterator function_begin;
+ struct vsir_program_iterator function_end;
struct vsir_block *blocks;
struct vsir_block *entry;
size_t block_count;
@@ -5046,10 +5256,11 @@ static void vsir_cfg_dump_structured_program(struct vsir_cfg *cfg)
}
static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program *program,
- struct vkd3d_shader_message_context *message_context, struct vsir_cfg_emit_target *target,
- size_t *pos)
+ struct vkd3d_shader_message_context *message_context,
+ struct vsir_cfg_emit_target *target, struct vsir_program_iterator *it)
{
struct vsir_block *current_block = NULL;
+ struct vkd3d_shader_instruction *ins;
enum vkd3d_result ret;
size_t i;
@@ -5058,7 +5269,7 @@ static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program
cfg->program = program;
cfg->block_count = program->block_count;
cfg->target = target;
- cfg->function_begin = *pos;
+ cfg->function_begin = *it;
vsir_block_list_init(&cfg->order);
@@ -5068,12 +5279,11 @@ static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program
if (TRACE_ON())
vkd3d_string_buffer_init(&cfg->debug_buffer);
- for (i = *pos; i < program->instructions.count; ++i)
+ for (ins = vsir_program_iterator_current(it); ins; ins = vsir_program_iterator_next(it))
{
- struct vkd3d_shader_instruction *instruction = &program->instructions.elements[i];
bool finish = false;
- switch (instruction->opcode)
+ switch (ins->opcode)
{
case VSIR_OP_PHI:
case VSIR_OP_SWITCH_MONOLITHIC:
@@ -5081,7 +5291,7 @@ static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program
case VSIR_OP_LABEL:
{
- unsigned int label = label_from_src_param(&instruction->src[0]);
+ unsigned int label = label_from_src_param(&ins->src[0]);
VKD3D_ASSERT(!current_block);
VKD3D_ASSERT(label > 0);
@@ -5090,7 +5300,8 @@ static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program
VKD3D_ASSERT(current_block->label == 0);
if ((ret = vsir_block_init(current_block, label, program->block_count)) < 0)
goto fail;
- current_block->begin = &program->instructions.elements[i + 1];
+ current_block->begin = vsir_program_iterator_next(it);
+ vsir_program_iterator_prev(it);
if (!cfg->entry)
cfg->entry = current_block;
break;
@@ -5099,7 +5310,7 @@ static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program
case VSIR_OP_BRANCH:
case VSIR_OP_RET:
VKD3D_ASSERT(current_block);
- current_block->end = instruction;
+ current_block->end = ins;
current_block = NULL;
break;
@@ -5118,8 +5329,7 @@ static enum vkd3d_result vsir_cfg_init(struct vsir_cfg *cfg, struct vsir_program
break;
}
- *pos = i;
- cfg->function_end = *pos;
+ cfg->function_end = *it;
for (i = 0; i < cfg->block_count; ++i)
{
@@ -6616,13 +6826,13 @@ static enum vkd3d_result vsir_cfg_emit_structured_program(struct vsir_cfg *cfg)
}
static enum vkd3d_result vsir_program_structurize_function(struct vsir_program *program,
- struct vkd3d_shader_message_context *message_context, struct vsir_cfg_emit_target *target,
- size_t *pos)
+ struct vkd3d_shader_message_context *message_context,
+ struct vsir_cfg_emit_target *target, struct vsir_program_iterator *it)
{
enum vkd3d_result ret;
struct vsir_cfg cfg;
- if ((ret = vsir_cfg_init(&cfg, program, message_context, target, pos)) < 0)
+ if ((ret = vsir_cfg_init(&cfg, program, message_context, target, it)) < 0)
return ret;
vsir_cfg_compute_dominators(&cfg);
@@ -6653,10 +6863,11 @@ out:
static enum vkd3d_result vsir_program_structurize(struct vsir_program *program,
struct vsir_transformation_context *ctx)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
struct vkd3d_shader_message_context *message_context = ctx->message_context;
struct vsir_cfg_emit_target target = {0};
+ struct vkd3d_shader_instruction *ins;
enum vkd3d_result ret;
- size_t i;
VKD3D_ASSERT(program->cf_type == VSIR_CF_BLOCKS);
@@ -6666,19 +6877,17 @@ static enum vkd3d_result vsir_program_structurize(struct vsir_program *program,
if (!reserve_instructions(&target.instructions, &target.ins_capacity, program->instructions.count))
return VKD3D_ERROR_OUT_OF_MEMORY;
- for (i = 0; i < program->instructions.count;)
+ for (ins = vsir_program_iterator_head(&it); ins;)
{
- struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
-
switch (ins->opcode)
{
case VSIR_OP_LABEL:
VKD3D_ASSERT(program->shader_version.type != VKD3D_SHADER_TYPE_HULL);
TRACE("Structurizing a non-hull shader.\n");
- if ((ret = vsir_program_structurize_function(program, message_context,
- &target, &i)) < 0)
+ if ((ret = vsir_program_structurize_function(program, message_context, &target, &it)) < 0)
goto fail;
- VKD3D_ASSERT(i == program->instructions.count);
+ ins = vsir_program_iterator_current(&it);
+ VKD3D_ASSERT(!ins);
break;
case VSIR_OP_HS_CONTROL_POINT_PHASE:
@@ -6687,17 +6896,17 @@ static enum vkd3d_result vsir_program_structurize(struct vsir_program *program,
VKD3D_ASSERT(program->shader_version.type == VKD3D_SHADER_TYPE_HULL);
TRACE("Structurizing phase %u of a hull shader.\n", ins->opcode);
target.instructions[target.ins_count++] = *ins;
- ++i;
- if ((ret = vsir_program_structurize_function(program, message_context,
- &target, &i)) < 0)
+ vsir_program_iterator_next(&it);
+ if ((ret = vsir_program_structurize_function(program, message_context, &target, &it)) < 0)
goto fail;
+ ins = vsir_program_iterator_current(&it);
break;
default:
if (!reserve_instructions(&target.instructions, &target.ins_capacity, target.ins_count + 1))
return VKD3D_ERROR_OUT_OF_MEMORY;
target.instructions[target.ins_count++] = *ins;
- ++i;
+ ins = vsir_program_iterator_next(&it);
break;
}
}
@@ -6742,8 +6951,10 @@ static void register_map_undominated_use(struct vkd3d_shader_register *reg, stru
static enum vkd3d_result vsir_cfg_materialize_undominated_ssas_to_temps(struct vsir_cfg *cfg)
{
struct vsir_program *program = cfg->program;
+ struct vkd3d_shader_instruction *ins, *end;
struct ssas_to_temps_alloc alloc = {0};
struct vsir_block **origin_blocks;
+ struct vsir_program_iterator it;
unsigned int j;
size_t i;
@@ -6761,7 +6972,6 @@ static enum vkd3d_result vsir_cfg_materialize_undominated_ssas_to_temps(struct v
for (i = 0; i < cfg->block_count; ++i)
{
struct vsir_block *block = &cfg->blocks[i];
- struct vkd3d_shader_instruction *ins;
if (block->label == 0)
continue;
@@ -6779,7 +6989,6 @@ static enum vkd3d_result vsir_cfg_materialize_undominated_ssas_to_temps(struct v
for (i = 0; i < cfg->block_count; ++i)
{
struct vsir_block *block = &cfg->blocks[i];
- struct vkd3d_shader_instruction *ins;
if (block->label == 0)
continue;
@@ -6796,10 +7005,10 @@ static enum vkd3d_result vsir_cfg_materialize_undominated_ssas_to_temps(struct v
TRACE("Emitting temps for %u values with undominated usage.\n", alloc.next_temp_idx - program->temp_count);
- for (i = cfg->function_begin; i < cfg->function_end; ++i)
+ it = cfg->function_begin;
+ end = vsir_program_iterator_current(&cfg->function_end);
+ for (ins = vsir_program_iterator_current(&it); ins != end; ins = vsir_program_iterator_next(&it))
{
- struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
-
for (j = 0; j < ins->dst_count; ++j)
materialize_ssas_to_temps_process_reg(program, &alloc, &ins->dst[j].reg);
@@ -6815,14 +7024,13 @@ done:
return VKD3D_OK;
}
-static enum vkd3d_result vsir_program_materialize_undominated_ssas_to_temps_in_function(
- struct vsir_program *program, struct vkd3d_shader_message_context *message_context,
- size_t *pos)
+static enum vkd3d_result vsir_program_materialize_undominated_ssas_to_temps_in_function(struct vsir_program *program,
+ struct vkd3d_shader_message_context *message_context, struct vsir_program_iterator *it)
{
enum vkd3d_result ret;
struct vsir_cfg cfg;
- if ((ret = vsir_cfg_init(&cfg, program, message_context, NULL, pos)) < 0)
+ if ((ret = vsir_cfg_init(&cfg, program, message_context, NULL, it)) < 0)
return ret;
vsir_cfg_compute_dominators(&cfg);
@@ -6837,25 +7045,25 @@ static enum vkd3d_result vsir_program_materialize_undominated_ssas_to_temps_in_f
static enum vkd3d_result vsir_program_materialize_undominated_ssas_to_temps(struct vsir_program *program,
struct vsir_transformation_context *ctx)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
struct vkd3d_shader_message_context *message_context = ctx->message_context;
+ struct vkd3d_shader_instruction *ins;
enum vkd3d_result ret;
- size_t i;
VKD3D_ASSERT(program->cf_type == VSIR_CF_BLOCKS);
- for (i = 0; i < program->instructions.count;)
+ for (ins = vsir_program_iterator_head(&it); ins;)
{
- struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
-
switch (ins->opcode)
{
case VSIR_OP_LABEL:
VKD3D_ASSERT(program->shader_version.type != VKD3D_SHADER_TYPE_HULL);
TRACE("Materializing undominated SSAs in a non-hull shader.\n");
if ((ret = vsir_program_materialize_undominated_ssas_to_temps_in_function(
- program, message_context, &i)) < 0)
+ program, message_context, &it)) < 0)
return ret;
- VKD3D_ASSERT(i == program->instructions.count);
+ ins = vsir_program_iterator_current(&it);
+ VKD3D_ASSERT(!ins);
break;
case VSIR_OP_HS_CONTROL_POINT_PHASE:
@@ -6863,14 +7071,15 @@ static enum vkd3d_result vsir_program_materialize_undominated_ssas_to_temps(stru
case VSIR_OP_HS_JOIN_PHASE:
VKD3D_ASSERT(program->shader_version.type == VKD3D_SHADER_TYPE_HULL);
TRACE("Materializing undominated SSAs in phase %u of a hull shader.\n", ins->opcode);
- ++i;
+ vsir_program_iterator_next(&it);
if ((ret = vsir_program_materialize_undominated_ssas_to_temps_in_function(
- program, message_context, &i)) < 0)
+ program, message_context, &it)) < 0)
return ret;
+ ins = vsir_program_iterator_current(&it);
break;
default:
- ++i;
+ ins = vsir_program_iterator_next(&it);
break;
}
}
@@ -6881,7 +7090,6 @@ static enum vkd3d_result vsir_program_materialize_undominated_ssas_to_temps(stru
static bool use_flat_interpolation(const struct vsir_program *program,
struct vkd3d_shader_message_context *message_context, bool *flat)
{
- static const struct vkd3d_shader_location no_loc;
const struct vkd3d_shader_parameter1 *parameter;
*flat = false;
@@ -6891,13 +7099,13 @@ static bool use_flat_interpolation(const struct vsir_program *program,
if (parameter->type != VKD3D_SHADER_PARAMETER_TYPE_IMMEDIATE_CONSTANT)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
"Unsupported flat interpolation parameter type %#x.", parameter->type);
return false;
}
if (parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_UINT32)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid flat interpolation parameter data type %#x.", parameter->data_type);
return false;
}
@@ -6938,7 +7146,6 @@ static enum vkd3d_result insert_alpha_test_before_ret(struct vsir_program *progr
uint32_t colour_temp, struct vkd3d_shader_message_context *message_context)
{
struct vkd3d_shader_location loc = vsir_program_iterator_current(it)->location;
- static const struct vkd3d_shader_location no_loc;
struct vkd3d_shader_instruction *ins;
static const struct
@@ -6959,10 +7166,8 @@ static enum vkd3d_result insert_alpha_test_before_ret(struct vsir_program *progr
if (compare_func == VKD3D_SHADER_COMPARISON_FUNC_NEVER)
{
- vsir_program_iterator_prev(it);
- if (!vsir_program_iterator_insert_after(it, 1))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 1)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(it);
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_DISCARD, 0, 1);
ins->flags = VKD3D_SHADER_CONDITIONAL_OP_Z;
@@ -6972,10 +7177,8 @@ static enum vkd3d_result insert_alpha_test_before_ret(struct vsir_program *progr
return VKD3D_OK;
}
- vsir_program_iterator_prev(it);
- if (!vsir_program_iterator_insert_after(it, 3))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 3)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(it);
switch (ref->data_type)
{
@@ -6994,7 +7197,7 @@ static enum vkd3d_result insert_alpha_test_before_ret(struct vsir_program *progr
break;
case VKD3D_SHADER_PARAMETER_DATA_TYPE_FLOAT32_VEC4:
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_PARAMETER,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_PARAMETER,
"Alpha test reference data type must be a single component.");
return VKD3D_ERROR_INVALID_ARGUMENT;
@@ -7036,7 +7239,6 @@ static enum vkd3d_result vsir_program_insert_alpha_test(struct vsir_program *pro
struct vkd3d_shader_message_context *message_context = ctx->message_context;
const struct vkd3d_shader_parameter1 *func = NULL, *ref = NULL;
uint32_t colour_signature_idx, colour_temp = ~0u;
- static const struct vkd3d_shader_location no_loc;
enum vkd3d_shader_comparison_func compare_func;
struct vkd3d_shader_instruction *ins;
int ret;
@@ -7054,13 +7256,13 @@ static enum vkd3d_result vsir_program_insert_alpha_test(struct vsir_program *pro
if (func->type != VKD3D_SHADER_PARAMETER_TYPE_IMMEDIATE_CONSTANT)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
"Unsupported alpha test function parameter type %#x.", func->type);
return VKD3D_ERROR_NOT_IMPLEMENTED;
}
if (func->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_UINT32)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid alpha test function parameter data type %#x.", func->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7117,10 +7319,8 @@ static enum vkd3d_result insert_clip_planes_before_ret(struct vsir_program *prog
struct vkd3d_shader_instruction *ins;
unsigned int output_idx = 0;
- vsir_program_iterator_prev(it);
- if (!vsir_program_iterator_insert_after(it, vkd3d_popcount(mask) + 1))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, vkd3d_popcount(mask) + 1)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(it);
for (unsigned int i = 0; i < 8; ++i)
{
@@ -7166,7 +7366,6 @@ static enum vkd3d_result vsir_program_insert_clip_planes(struct vsir_program *pr
unsigned int low_signature_idx = ~0u, high_signature_idx = ~0u;
const struct vkd3d_shader_parameter1 *mask_parameter = NULL;
uint32_t position_signature_idx, position_temp, mask;
- static const struct vkd3d_shader_location no_loc;
struct signature_element *clip_element;
struct vkd3d_shader_instruction *ins;
unsigned int plane_count;
@@ -7188,13 +7387,13 @@ static enum vkd3d_result vsir_program_insert_clip_planes(struct vsir_program *pr
if (mask_parameter->type != VKD3D_SHADER_PARAMETER_TYPE_IMMEDIATE_CONSTANT)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
"Unsupported clip plane mask parameter type %#x.", mask_parameter->type);
return VKD3D_ERROR_NOT_IMPLEMENTED;
}
if (mask_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_UINT32)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid clip plane mask parameter data type %#x.", mask_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7207,7 +7406,7 @@ static enum vkd3d_result vsir_program_insert_clip_planes(struct vsir_program *pr
{
if (signature->elements[i].sysval_semantic == VKD3D_SHADER_SV_CLIP_DISTANCE)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_PARAMETER,
+ vkd3d_shader_error(ctx->message_context, &ctx->null_location, VKD3D_SHADER_ERROR_VSIR_INVALID_PARAMETER,
"Clip planes cannot be used if the shader writes clip distance.");
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7215,7 +7414,7 @@ static enum vkd3d_result vsir_program_insert_clip_planes(struct vsir_program *pr
if (!vsir_signature_find_sysval(signature, VKD3D_SHADER_SV_POSITION, 0, &position_signature_idx))
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_MISSING_SEMANTIC,
+ vkd3d_shader_error(ctx->message_context, &ctx->null_location, VKD3D_SHADER_ERROR_VSIR_MISSING_SEMANTIC,
"Shader does not write position.");
return VKD3D_ERROR_INVALID_SHADER;
}
@@ -7288,10 +7487,8 @@ static enum vkd3d_result insert_point_size_before_ret(struct vsir_program *progr
const struct vkd3d_shader_location loc = vsir_program_iterator_current(it)->location;
struct vkd3d_shader_instruction *ins;
- vsir_program_iterator_prev(it);
- if (!vsir_program_iterator_insert_after(it, 1))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 1)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(it);
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MOV, 1, 1);
vsir_dst_param_init(&ins->dst[0], VKD3DSPR_RASTOUT, VSIR_DATA_F32, 1);
@@ -7307,7 +7504,6 @@ static enum vkd3d_result vsir_program_insert_point_size(struct vsir_program *pro
{
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
const struct vkd3d_shader_parameter1 *size_parameter = NULL;
- static const struct vkd3d_shader_location no_loc;
struct vkd3d_shader_instruction *ins;
if (program->has_point_size)
@@ -7329,7 +7525,7 @@ static enum vkd3d_result vsir_program_insert_point_size(struct vsir_program *pro
if (size_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_FLOAT32)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid point size parameter data type %#x.", size_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7356,7 +7552,6 @@ static enum vkd3d_result vsir_program_insert_point_size_clamp(struct vsir_progra
{
const struct vkd3d_shader_parameter1 *min_parameter = NULL, *max_parameter = NULL;
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
- static const struct vkd3d_shader_location no_loc;
struct vkd3d_shader_instruction *ins;
if (!program->has_point_size)
@@ -7380,14 +7575,14 @@ static enum vkd3d_result vsir_program_insert_point_size_clamp(struct vsir_progra
if (min_parameter && min_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_FLOAT32)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid minimum point size parameter data type %#x.", min_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
if (max_parameter && max_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_FLOAT32)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid maximum point size parameter data type %#x.", max_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7530,7 +7725,7 @@ static enum vkd3d_result vsir_program_insert_point_coord(struct vsir_program *pr
{
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions), it2;
const struct vkd3d_shader_parameter1 *sprite_parameter = NULL;
- static const struct vkd3d_shader_location no_loc;
+ struct vkd3d_shader_location loc = ctx->null_location;
struct vkd3d_shader_instruction *ins;
bool used_texcoord = false;
unsigned int coord_temp;
@@ -7552,13 +7747,13 @@ static enum vkd3d_result vsir_program_insert_point_coord(struct vsir_program *pr
if (sprite_parameter->type != VKD3D_SHADER_PARAMETER_TYPE_IMMEDIATE_CONSTANT)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
"Unsupported point sprite parameter type %#x.", sprite_parameter->type);
return VKD3D_ERROR_NOT_IMPLEMENTED;
}
if (sprite_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_UINT32)
{
- vkd3d_shader_error(ctx->message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(ctx->message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid point sprite parameter data type %#x.", sprite_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7578,7 +7773,10 @@ static enum vkd3d_result vsir_program_insert_point_coord(struct vsir_program *pr
for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
if (!vsir_instruction_is_dcl(ins) && ins->opcode != VSIR_OP_LABEL && ins->opcode != VSIR_OP_NOP)
+ {
+ loc = ins->location;
break;
+ }
}
it2 = it;
@@ -7613,12 +7811,10 @@ static enum vkd3d_result vsir_program_insert_point_coord(struct vsir_program *pr
if (used_texcoord)
{
- vsir_program_iterator_prev(&it);
- if (!vsir_program_iterator_insert_after(&it, 2))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(&it, 2)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = vsir_program_iterator_next(&it);
- vsir_instruction_init_with_params(program, ins, &no_loc, VSIR_OP_MOV, 1, 1);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MOV, 1, 1);
dst_param_init_temp_float4(&ins->dst[0], coord_temp);
ins->dst[0].write_mask = VKD3DSP_WRITEMASK_0 | VKD3DSP_WRITEMASK_1;
vsir_src_param_init(&ins->src[0], VKD3DSPR_POINT_COORD, VSIR_DATA_F32, 0);
@@ -7626,7 +7822,7 @@ static enum vkd3d_result vsir_program_insert_point_coord(struct vsir_program *pr
ins->src[0].swizzle = VKD3D_SHADER_NO_SWIZZLE;
ins = vsir_program_iterator_next(&it);
- vsir_instruction_init_with_params(program, ins, &no_loc, VSIR_OP_MOV, 1, 1);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MOV, 1, 1);
dst_param_init_temp_float4(&ins->dst[0], coord_temp);
ins->dst[0].write_mask = VKD3DSP_WRITEMASK_2 | VKD3DSP_WRITEMASK_3;
vsir_src_param_init(&ins->src[0], VKD3DSPR_IMMCONST, VSIR_DATA_F32, 0);
@@ -7668,15 +7864,12 @@ static enum vkd3d_result vsir_program_add_fog_input(struct vsir_program *program
}
static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *program,
- const struct vkd3d_shader_instruction *ret, enum vkd3d_shader_fog_fragment_mode mode,
- uint32_t fog_signature_idx, uint32_t colour_signature_idx, uint32_t colour_temp,
- size_t *ret_pos, struct vkd3d_shader_message_context *message_context)
+ struct vsir_program_iterator *it, enum vkd3d_shader_fog_fragment_mode mode, uint32_t fog_signature_idx,
+ uint32_t colour_signature_idx, uint32_t colour_temp, struct vkd3d_shader_message_context *message_context)
{
- struct vkd3d_shader_instruction_array *instructions = &program->instructions;
- struct vkd3d_shader_location loc = ret->location;
+ struct vkd3d_shader_instruction *ins = vsir_program_iterator_current(it);
+ struct vkd3d_shader_location loc = ins->location;
uint32_t ssa_factor = program->ssa_count++;
- size_t pos = ret - instructions->elements;
- struct vkd3d_shader_instruction *ins;
uint32_t ssa_temp, ssa_temp2;
switch (mode)
@@ -7687,16 +7880,11 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
* add sr0, FOG_END, -vFOG.x
* mul_sat srFACTOR, sr0, FOG_SCALE
*/
- if (!shader_instruction_array_insert_at(&program->instructions, pos, 4))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 4)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ret = NULL;
-
- *ret_pos = pos + 4;
ssa_temp = program->ssa_count++;
- ins = &program->instructions.elements[pos];
-
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_ADD, 1, 2);
dst_param_init_ssa_float(&ins->dst[0], ssa_temp);
src_param_init_parameter(&ins->src[0], VKD3D_SHADER_PARAMETER_NAME_FOG_END, VSIR_DATA_F32);
@@ -7705,12 +7893,15 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
ins->src[1].reg.dimension = VSIR_DIMENSION_VEC4;
ins->src[1].swizzle = VKD3D_SHADER_SWIZZLE(X, X, X, X);
ins->src[1].modifiers = VKD3DSPSM_NEG;
+ ins = vsir_program_iterator_next(it);
- vsir_instruction_init_with_params(program, ++ins, &loc, VSIR_OP_MUL, 1, 2);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MUL, 1, 2);
dst_param_init_ssa_float(&ins->dst[0], ssa_factor);
ins->dst[0].modifiers = VKD3DSPDM_SATURATE;
src_param_init_ssa_float(&ins->src[0], ssa_temp);
src_param_init_parameter(&ins->src[1], VKD3D_SHADER_PARAMETER_NAME_FOG_SCALE, VSIR_DATA_F32);
+ ins = vsir_program_iterator_next(it);
+
break;
case VKD3D_SHADER_FOG_FRAGMENT_EXP:
@@ -7719,16 +7910,11 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
* mul sr0, FOG_SCALE, vFOG.x
* exp_sat srFACTOR, -sr0
*/
- if (!shader_instruction_array_insert_at(&program->instructions, pos, 4))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 4)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ret = NULL;
-
- *ret_pos = pos + 4;
ssa_temp = program->ssa_count++;
- ins = &program->instructions.elements[pos];
-
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MUL, 1, 2);
dst_param_init_ssa_float(&ins->dst[0], ssa_temp);
src_param_init_parameter(&ins->src[0], VKD3D_SHADER_PARAMETER_NAME_FOG_SCALE, VSIR_DATA_F32);
@@ -7736,12 +7922,14 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
ins->src[1].reg.idx[0].offset = fog_signature_idx;
ins->src[1].reg.dimension = VSIR_DIMENSION_VEC4;
ins->src[1].swizzle = VKD3D_SHADER_SWIZZLE(X, X, X, X);
+ ins = vsir_program_iterator_next(it);
- vsir_instruction_init_with_params(program, ++ins, &loc, VSIR_OP_EXP, 1, 1);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_EXP, 1, 1);
dst_param_init_ssa_float(&ins->dst[0], ssa_factor);
ins->dst[0].modifiers = VKD3DSPDM_SATURATE;
src_param_init_ssa_float(&ins->src[0], ssa_temp);
ins->src[0].modifiers = VKD3DSPSM_NEG;
+ ins = vsir_program_iterator_next(it);
break;
case VKD3D_SHADER_FOG_FRAGMENT_EXP2:
@@ -7751,17 +7939,12 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
* mul sr1, sr0, sr0
* exp_sat srFACTOR, -sr1
*/
- if (!shader_instruction_array_insert_at(&program->instructions, pos, 5))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 5)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ret = NULL;
-
- *ret_pos = pos + 5;
ssa_temp = program->ssa_count++;
ssa_temp2 = program->ssa_count++;
- ins = &program->instructions.elements[pos];
-
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MUL, 1, 2);
dst_param_init_ssa_float(&ins->dst[0], ssa_temp);
src_param_init_parameter(&ins->src[0], VKD3D_SHADER_PARAMETER_NAME_FOG_SCALE, VSIR_DATA_F32);
@@ -7769,17 +7952,20 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
ins->src[1].reg.idx[0].offset = fog_signature_idx;
ins->src[1].reg.dimension = VSIR_DIMENSION_VEC4;
ins->src[1].swizzle = VKD3D_SHADER_SWIZZLE(X, X, X, X);
+ ins = vsir_program_iterator_next(it);
- vsir_instruction_init_with_params(program, ++ins, &loc, VSIR_OP_MUL, 1, 2);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MUL, 1, 2);
dst_param_init_ssa_float(&ins->dst[0], ssa_temp2);
src_param_init_ssa_float(&ins->src[0], ssa_temp);
src_param_init_ssa_float(&ins->src[1], ssa_temp);
+ ins = vsir_program_iterator_next(it);
- vsir_instruction_init_with_params(program, ++ins, &loc, VSIR_OP_EXP, 1, 1);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_EXP, 1, 1);
dst_param_init_ssa_float(&ins->dst[0], ssa_factor);
ins->dst[0].modifiers = VKD3DSPDM_SATURATE;
src_param_init_ssa_float(&ins->src[0], ssa_temp2);
ins->src[0].modifiers = VKD3DSPSM_NEG;
+ ins = vsir_program_iterator_next(it);
break;
default:
@@ -7792,18 +7978,20 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
* mad oC0, sr0, srFACTOR, FOG_COLOUR
*/
- vsir_instruction_init_with_params(program, ++ins, &loc, VSIR_OP_ADD, 1, 2);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_ADD, 1, 2);
dst_param_init_ssa_float4(&ins->dst[0], program->ssa_count++);
src_param_init_temp_float4(&ins->src[0], colour_temp);
src_param_init_parameter_vec4(&ins->src[1], VKD3D_SHADER_PARAMETER_NAME_FOG_COLOUR, VSIR_DATA_F32);
ins->src[1].modifiers = VKD3DSPSM_NEG;
+ ins = vsir_program_iterator_next(it);
- vsir_instruction_init_with_params(program, ++ins, &loc, VSIR_OP_MAD, 1, 3);
+ vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MAD, 1, 3);
dst_param_init_output(&ins->dst[0], VSIR_DATA_F32, colour_signature_idx,
program->output_signature.elements[colour_signature_idx].mask);
src_param_init_ssa_float4(&ins->src[0], program->ssa_count - 1);
src_param_init_ssa_float(&ins->src[1], ssa_factor);
src_param_init_parameter_vec4(&ins->src[2], VKD3D_SHADER_PARAMETER_NAME_FOG_COLOUR, VSIR_DATA_F32);
+ ins = vsir_program_iterator_next(it);
return VKD3D_OK;
}
@@ -7811,14 +7999,13 @@ static enum vkd3d_result insert_fragment_fog_before_ret(struct vsir_program *pro
static enum vkd3d_result vsir_program_insert_fragment_fog(struct vsir_program *program,
struct vsir_transformation_context *ctx)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
struct vkd3d_shader_message_context *message_context = ctx->message_context;
uint32_t colour_signature_idx, fog_signature_idx, colour_temp;
const struct vkd3d_shader_parameter1 *mode_parameter = NULL;
- static const struct vkd3d_shader_location no_loc;
const struct signature_element *fog_element;
enum vkd3d_shader_fog_fragment_mode mode;
struct vkd3d_shader_instruction *ins;
- size_t new_pos;
int ret;
if (program->shader_version.type != VKD3D_SHADER_TYPE_PIXEL)
@@ -7832,13 +8019,13 @@ static enum vkd3d_result vsir_program_insert_fragment_fog(struct vsir_program *p
if (mode_parameter->type != VKD3D_SHADER_PARAMETER_TYPE_IMMEDIATE_CONSTANT)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
"Unsupported fog fragment mode parameter type %#x.", mode_parameter->type);
return VKD3D_ERROR_NOT_IMPLEMENTED;
}
if (mode_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_UINT32)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid fog fragment mode parameter data type %#x.", mode_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -7859,19 +8046,16 @@ static enum vkd3d_result vsir_program_insert_fragment_fog(struct vsir_program *p
* through the whole shader and convert it to a temp. */
colour_temp = program->temp_count++;
- for (size_t i = 0; i < program->instructions.count; ++i)
+ for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
- ins = &program->instructions.elements[i];
-
if (vsir_instruction_is_dcl(ins))
continue;
if (ins->opcode == VSIR_OP_RET)
{
- if ((ret = insert_fragment_fog_before_ret(program, ins, mode, fog_signature_idx,
- colour_signature_idx, colour_temp, &new_pos, message_context)) < 0)
+ if ((ret = insert_fragment_fog_before_ret(program, &it, mode, fog_signature_idx,
+ colour_signature_idx, colour_temp, message_context)) < 0)
return ret;
- i = new_pos;
continue;
}
@@ -7927,21 +8111,16 @@ static enum vkd3d_result vsir_program_add_fog_output(struct vsir_program *progra
return VKD3D_OK;
}
-static enum vkd3d_result insert_vertex_fog_before_ret(struct vsir_program *program,
- const struct vkd3d_shader_instruction *ret, enum vkd3d_shader_fog_source source, uint32_t temp,
- uint32_t fog_signature_idx, uint32_t source_signature_idx, size_t *ret_pos)
+static enum vkd3d_result insert_vertex_fog_before_ret(struct vsir_program *program, struct vsir_program_iterator *it,
+ enum vkd3d_shader_fog_source source, uint32_t temp, uint32_t fog_signature_idx, uint32_t source_signature_idx)
{
const struct signature_element *e = &program->output_signature.elements[source_signature_idx];
- struct vkd3d_shader_instruction_array *instructions = &program->instructions;
+ struct vkd3d_shader_instruction *ret = vsir_program_iterator_current(it);
const struct vkd3d_shader_location loc = ret->location;
- size_t pos = ret - instructions->elements;
struct vkd3d_shader_instruction *ins;
- if (!shader_instruction_array_insert_at(&program->instructions, pos, 2))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(it, 2)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ret = NULL;
-
- ins = &program->instructions.elements[pos];
/* Write the fog output. */
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MOV, 1, 1);
@@ -7951,26 +8130,26 @@ static enum vkd3d_result insert_vertex_fog_before_ret(struct vsir_program *progr
ins->src[0].swizzle = VKD3D_SHADER_SWIZZLE(Z, Z, Z, Z);
else /* Position or specular W. */
ins->src[0].swizzle = VKD3D_SHADER_SWIZZLE(W, W, W, W);
- ++ins;
+ ins = vsir_program_iterator_next(it);
/* Write the position or specular output. */
vsir_instruction_init_with_params(program, ins, &loc, VSIR_OP_MOV, 1, 1);
dst_param_init_output(&ins->dst[0], vsir_data_type_from_component_type(e->component_type),
source_signature_idx, e->mask);
src_param_init_temp_float4(&ins->src[0], temp);
- ++ins;
+ ins = vsir_program_iterator_next(it);
- *ret_pos = pos + 2;
return VKD3D_OK;
}
static enum vkd3d_result vsir_program_insert_vertex_fog(struct vsir_program *program,
struct vsir_transformation_context *ctx)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
struct vkd3d_shader_message_context *message_context = ctx->message_context;
const struct vkd3d_shader_parameter1 *source_parameter = NULL;
uint32_t fog_signature_idx, source_signature_idx, temp;
- static const struct vkd3d_shader_location no_loc;
+ struct vkd3d_shader_instruction *ins;
enum vkd3d_shader_fog_source source;
const struct signature_element *e;
@@ -7982,13 +8161,13 @@ static enum vkd3d_result vsir_program_insert_vertex_fog(struct vsir_program *pro
if (source_parameter->type != VKD3D_SHADER_PARAMETER_TYPE_IMMEDIATE_CONSTANT)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_NOT_IMPLEMENTED,
"Unsupported fog source parameter type %#x.", source_parameter->type);
return VKD3D_ERROR_NOT_IMPLEMENTED;
}
if (source_parameter->data_type != VKD3D_SHADER_PARAMETER_DATA_TYPE_UINT32)
{
- vkd3d_shader_error(message_context, &no_loc, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
+ vkd3d_shader_error(message_context, NULL, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
"Invalid fog source parameter data type %#x.", source_parameter->data_type);
return VKD3D_ERROR_INVALID_ARGUMENT;
}
@@ -8010,7 +8189,7 @@ static enum vkd3d_result vsir_program_insert_vertex_fog(struct vsir_program *pro
if (!vsir_signature_find_sysval(&program->output_signature,
VKD3D_SHADER_SV_POSITION, 0, &source_signature_idx))
{
- vkd3d_shader_error(ctx->message_context, &no_loc,
+ vkd3d_shader_error(ctx->message_context, &ctx->null_location,
VKD3D_SHADER_ERROR_VSIR_MISSING_SEMANTIC, "Shader does not write position.");
return VKD3D_ERROR_INVALID_SHADER;
}
@@ -8027,22 +8206,18 @@ static enum vkd3d_result vsir_program_insert_vertex_fog(struct vsir_program *pro
/* Insert a fog write before each ret, and convert either specular or
* position output to a temp. */
- for (size_t i = 0; i < program->instructions.count; ++i)
+ for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
- struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
-
if (vsir_instruction_is_dcl(ins))
continue;
if (ins->opcode == VSIR_OP_RET)
{
- size_t new_pos;
int ret;
- if ((ret = insert_vertex_fog_before_ret(program, ins, source, temp,
- fog_signature_idx, source_signature_idx, &new_pos)) < 0)
+ if ((ret = insert_vertex_fog_before_ret(program, &it, source, temp,
+ fog_signature_idx, source_signature_idx)) < 0)
return ret;
- i = new_pos;
continue;
}
@@ -8450,7 +8625,7 @@ struct liveness_tracker
bool fixed_mask;
uint8_t mask;
unsigned int first_write, last_access;
- } *ssa_regs;
+ } *ssa_regs, *temp_regs;
};
static void liveness_track_src(struct liveness_tracker *tracker,
@@ -8464,6 +8639,8 @@ static void liveness_track_src(struct liveness_tracker *tracker,
if (src->reg.type == VKD3DSPR_SSA)
tracker->ssa_regs[src->reg.idx[0].offset].last_access = index;
+ else if (src->reg.type == VKD3DSPR_TEMP)
+ tracker->temp_regs[src->reg.idx[0].offset].last_access = index;
}
static void liveness_track_dst(struct liveness_tracker *tracker, struct vkd3d_shader_dst_param *dst,
@@ -8479,6 +8656,8 @@ static void liveness_track_dst(struct liveness_tracker *tracker, struct vkd3d_sh
if (dst->reg.type == VKD3DSPR_SSA)
reg = &tracker->ssa_regs[dst->reg.idx[0].offset];
+ else if (dst->reg.type == VKD3DSPR_TEMP)
+ reg = &tracker->temp_regs[dst->reg.idx[0].offset];
else
return;
@@ -8565,20 +8744,22 @@ static void liveness_tracker_cleanup(struct liveness_tracker *tracker)
static enum vkd3d_result track_liveness(struct vsir_program *program, struct liveness_tracker *tracker)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
+ struct vkd3d_shader_instruction *ins;
struct liveness_tracker_reg *regs;
unsigned int loop_depth = 0;
unsigned int loop_start = 0;
+ unsigned int i;
memset(tracker, 0, sizeof(*tracker));
- if (!(regs = vkd3d_calloc(program->ssa_count, sizeof(*regs))))
+ if (!(regs = vkd3d_calloc(program->ssa_count + program->temp_count, sizeof(*regs))))
return VKD3D_ERROR_OUT_OF_MEMORY;
tracker->ssa_regs = regs;
+ tracker->temp_regs = &regs[program->ssa_count];
- for (unsigned int i = 0; i < program->instructions.count; ++i)
+ for (ins = vsir_program_iterator_head(&it), i = 0; ins; ins = vsir_program_iterator_next(&it), ++i)
{
- const struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
-
if (ins->opcode == VSIR_OP_LOOP || ins->opcode == VSIR_OP_REP)
{
if (!loop_depth++)
@@ -8604,8 +8785,7 @@ static enum vkd3d_result track_liveness(struct vsir_program *program, struct liv
* should be illegal for an SSA value to be read in a block
* containing L.)
* We don't try to perform this optimization yet, in the name of
- * maximal simplicity, and also because this code is intended to
- * be extended to non-SSA values. */
+ * maximal simplicity. */
for (unsigned int j = 0; j < program->ssa_count; ++j)
{
struct liveness_tracker_reg *reg = &tracker->ssa_regs[j];
@@ -8615,6 +8795,16 @@ static enum vkd3d_result track_liveness(struct vsir_program *program, struct liv
if (reg->last_access < i)
reg->last_access = i;
}
+
+ for (unsigned int j = 0; j < program->temp_count; ++j)
+ {
+ struct liveness_tracker_reg *reg = &tracker->temp_regs[j];
+
+ if (reg->first_write > loop_start)
+ reg->first_write = loop_start;
+ if (reg->last_access < i)
+ reg->last_access = i;
+ }
}
}
@@ -8634,8 +8824,8 @@ struct temp_allocator
{
uint8_t allocated_mask;
uint32_t temp_id;
- } *ssa_regs;
- size_t allocated_ssa_count;
+ } *ssa_regs, *temp_regs;
+ size_t allocated_ssa_count, allocated_temp_count;
enum vkd3d_result result;
};
@@ -8662,16 +8852,30 @@ static uint8_t get_available_writemask(const struct temp_allocator *allocator,
return writemask;
}
+ for (size_t i = 0; i < allocator->allocated_temp_count; ++i)
+ {
+ const struct temp_allocator_reg *reg = &allocator->temp_regs[i];
+ const struct liveness_tracker_reg *liveness_reg = &tracker->temp_regs[i];
+
+ if (reg->temp_id == temp_id
+ && first_write < liveness_reg->last_access
+ && last_access > liveness_reg->first_write)
+ writemask &= ~reg->allocated_mask;
+
+ if (!writemask)
+ return writemask;
+ }
+
return writemask;
}
static bool temp_allocator_allocate(struct temp_allocator *allocator, struct liveness_tracker *tracker,
- struct temp_allocator_reg *reg, const struct liveness_tracker_reg *liveness_reg, uint32_t base_id)
+ struct temp_allocator_reg *reg, const struct liveness_tracker_reg *liveness_reg)
{
if (!liveness_reg->written)
return false;
- for (uint32_t id = base_id;; ++id)
+ for (uint32_t id = 0;; ++id)
{
uint8_t available_mask = get_available_writemask(allocator, tracker,
liveness_reg->first_write, liveness_reg->last_access, id);
@@ -8688,13 +8892,21 @@ static bool temp_allocator_allocate(struct temp_allocator *allocator, struct liv
else
{
/* For SSA values the mask is always zero-based and contiguous.
- * We don't correctly handle cases where it's not, currently. */
- VKD3D_ASSERT((liveness_reg->mask | (liveness_reg->mask - 1)) == liveness_reg->mask);
-
- if (vkd3d_popcount(available_mask) >= vkd3d_popcount(liveness_reg->mask))
+ * For TEMP values we assume the register was allocated that way,
+ * but it may only be partially used.
+ * We currently only handle cases where the mask is zero-based and
+ * contiguous, so we need to fill in the missing components to
+ * ensure this. */
+ uint8_t mask = (1u << (vkd3d_log2i(liveness_reg->mask) + 1)) - 1;
+
+ if (vkd3d_popcount(available_mask) >= vkd3d_popcount(mask))
{
+ if (mask != liveness_reg->mask)
+ WARN("Allocating a mask %#x with used components %#x; this is not optimized.\n",
+ mask, liveness_reg->mask);
+
reg->temp_id = id;
- reg->allocated_mask = vsir_combine_write_masks(available_mask, liveness_reg->mask);
+ reg->allocated_mask = vsir_combine_write_masks(available_mask, mask);
return true;
}
}
@@ -8713,6 +8925,8 @@ static void temp_allocator_set_src(struct temp_allocator *allocator, struct vkd3
if (src->reg.type == VKD3DSPR_SSA)
reg = &allocator->ssa_regs[src->reg.idx[0].offset];
+ else if (src->reg.type == VKD3DSPR_TEMP)
+ reg = &allocator->temp_regs[src->reg.idx[0].offset];
else
return;
@@ -8792,6 +9006,7 @@ static void temp_allocator_set_dst(struct temp_allocator *allocator,
struct vkd3d_shader_dst_param *dst, const struct vkd3d_shader_instruction *ins)
{
struct temp_allocator_reg *reg;
+ uint32_t remapped_mask;
for (unsigned int k = 0; k < dst->reg.idx_count; ++k)
{
@@ -8801,15 +9016,18 @@ static void temp_allocator_set_dst(struct temp_allocator *allocator,
if (dst->reg.type == VKD3DSPR_SSA)
reg = &allocator->ssa_regs[dst->reg.idx[0].offset];
+ else if (dst->reg.type == VKD3DSPR_TEMP)
+ reg = &allocator->temp_regs[dst->reg.idx[0].offset];
else
return;
dst->reg.type = VKD3DSPR_TEMP;
dst->reg.dimension = VSIR_DIMENSION_VEC4;
dst->reg.idx[0].offset = reg->temp_id;
- if (reg->allocated_mask != dst->write_mask)
+ remapped_mask = vsir_combine_write_masks(reg->allocated_mask, dst->write_mask);
+ if (dst->write_mask != remapped_mask)
{
- dst->write_mask = reg->allocated_mask;
+ dst->write_mask = remapped_mask;
if (vsir_opcode_is_double(ins->opcode))
{
@@ -8825,47 +9043,90 @@ static void temp_allocator_set_dst(struct temp_allocator *allocator,
if (vsir_src_is_masked(ins->opcode, i))
{
if (src->reg.type == VKD3DSPR_IMMCONST)
- vsir_remap_immconst(src, dst->write_mask);
+ vsir_remap_immconst(src, reg->allocated_mask);
else if (src->reg.type == VKD3DSPR_IMMCONST64)
- vsir_remap_immconst64(src, dst->write_mask);
+ vsir_remap_immconst64(src, reg->allocated_mask);
else
- src->swizzle = vsir_map_swizzle(src->swizzle, dst->write_mask);
+ src->swizzle = vsir_map_swizzle(src->swizzle, reg->allocated_mask);
}
}
}
}
+/* This pass does two things:
+ *
+ * - converts SSA registers (sr#) into temp registers (r#);
+ *
+ * - contracts temp registers with non-overlapping ranges by reallocating them
+ * into the same register.
+ *
+ * These are done at the same time so that SSA and temp registers with
+ * non-overlapping liveness can share the same register.
+ *
+ * The temp contraction is not particularly sophisticated. In particular, it
+ * does not detect cases where a single temp register has multiple disjoint
+ * ranges of liveness, and it also assumes that the components used by a single
+ * registers is zero-based and contiguous.
+ * The intent for temp contraction is that HLSL will output each distinct
+ * variable to a unique temp ID. */
enum vkd3d_result vsir_allocate_temp_registers(struct vsir_program *program,
struct vkd3d_shader_message_context *message_context)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
const unsigned int prev_temp_count = program->temp_count;
struct temp_allocator allocator = {0};
+ struct vkd3d_shader_instruction *ins;
struct temp_allocator_reg *regs;
struct liveness_tracker tracker;
enum vkd3d_result ret;
- if (!program->ssa_count)
+ if (!program->ssa_count && !prev_temp_count)
return VKD3D_OK;
if ((ret = track_liveness(program, &tracker)))
return ret;
- if (!(regs = vkd3d_calloc(program->ssa_count, sizeof(*regs))))
+ if (!(regs = vkd3d_calloc(program->ssa_count + prev_temp_count, sizeof(*regs))))
{
liveness_tracker_cleanup(&tracker);
return VKD3D_ERROR_OUT_OF_MEMORY;
}
allocator.message_context = message_context;
allocator.ssa_regs = regs;
+ allocator.temp_regs = regs + program->ssa_count;
+
+ program->temp_count = 0;
+
+ /* Reallocate temps first. We do this specifically to make sure that r0 is
+ * the first register to be allocated, and thus will be reallocated in
+ * place, and left alone.
+ * This is necessary because, in pixel shader model 1.x, r0 doubles as the
+ * output register, and needs to remain at r0. (Note that we need to already
+ * have the output in r0, rather than e.g. putting it in o0 and converting
+ * it to r0 after this pass, so that we know when r0 is live.) */
+ for (unsigned int i = 0; i < prev_temp_count; ++i)
+ {
+ const struct liveness_tracker_reg *liveness_reg = &tracker.temp_regs[i];
+ struct temp_allocator_reg *reg = &allocator.temp_regs[i];
+
+ if (temp_allocator_allocate(&allocator, &tracker, reg, liveness_reg))
+ {
+ TRACE("Reallocated r%u%s for r%u (liveness %u-%u).\n",
+ reg->temp_id, debug_vsir_writemask(reg->allocated_mask), i,
+ liveness_reg->first_write, liveness_reg->last_access);
+ program->temp_count = max(program->temp_count, reg->temp_id + 1);
+ }
+ ++allocator.allocated_temp_count;
+ }
for (unsigned int i = 0; i < program->ssa_count; ++i)
{
const struct liveness_tracker_reg *liveness_reg = &tracker.ssa_regs[i];
struct temp_allocator_reg *reg = &allocator.ssa_regs[i];
- if (temp_allocator_allocate(&allocator, &tracker, reg, liveness_reg, prev_temp_count))
+ if (temp_allocator_allocate(&allocator, &tracker, reg, liveness_reg))
{
- TRACE("Allocated r%u%s to sr%u (liveness %u-%u).\n",
+ TRACE("Allocated r%u%s for sr%u (liveness %u-%u).\n",
reg->temp_id, debug_vsir_writemask(reg->allocated_mask), i,
liveness_reg->first_write, liveness_reg->last_access);
program->temp_count = max(program->temp_count, reg->temp_id + 1);
@@ -8873,10 +9134,8 @@ enum vkd3d_result vsir_allocate_temp_registers(struct vsir_program *program,
++allocator.allocated_ssa_count;
}
- for (unsigned int i = 0; i < program->instructions.count; ++i)
+ for (ins = vsir_program_iterator_head(&it); ins; ins = vsir_program_iterator_next(&it))
{
- const struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
-
/* Make sure we do the srcs first; setting the dst writemask may need
* to remap their swizzles. */
for (unsigned int j = 0; j < ins->src_count; ++j)
@@ -8902,11 +9161,14 @@ enum vkd3d_result vsir_allocate_temp_registers(struct vsir_program *program,
enum vkd3d_result vsir_update_dcl_temps(struct vsir_program *program,
struct vkd3d_shader_message_context *message_context)
{
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
+ struct vkd3d_shader_location location;
+ struct vkd3d_shader_instruction *ins;
unsigned int temp_count = 0;
- for (int i = program->instructions.count - 1; i >= 0; --i)
+ for (ins = vsir_program_iterator_tail(&it); ins; ins = vsir_program_iterator_prev(&it))
{
- struct vkd3d_shader_instruction *ins = &program->instructions.elements[i];
+ location = ins->location;
if (ins->opcode == VSIR_OP_DCL_TEMPS)
{
@@ -8922,11 +9184,11 @@ enum vkd3d_result vsir_update_dcl_temps(struct vsir_program *program,
{
/* The phase didn't have a dcl_temps instruction, but we added
* temps here, so we need to insert one. */
- if (!shader_instruction_array_insert_at(&program->instructions, i + 1, 1))
+ if (!vsir_program_iterator_insert_after(&it, 1))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = &program->instructions.elements[i + 1];
- vsir_instruction_init(ins, &program->instructions.elements[i].location, VSIR_OP_DCL_TEMPS);
+ ins = vsir_program_iterator_next(&it);
+ vsir_instruction_init(ins, &location, VSIR_OP_DCL_TEMPS);
ins->declaration.count = temp_count;
temp_count = 0;
continue;
@@ -8947,13 +9209,13 @@ enum vkd3d_result vsir_update_dcl_temps(struct vsir_program *program,
if (temp_count && program->shader_version.major >= 4)
{
- struct vkd3d_shader_instruction *ins;
+ ins = vsir_program_iterator_head(&it);
+ location = ins->location;
- if (!shader_instruction_array_insert_at(&program->instructions, 0, 1))
+ if (!(ins = vsir_program_iterator_insert_before_and_move(&it, 1)))
return VKD3D_ERROR_OUT_OF_MEMORY;
- ins = &program->instructions.elements[0];
- vsir_instruction_init(ins, &program->instructions.elements[1].location, VSIR_OP_DCL_TEMPS);
+ vsir_instruction_init(ins, &location, VSIR_OP_DCL_TEMPS);
ins->declaration.count = temp_count;
}
@@ -8965,7 +9227,7 @@ struct validation_context
struct vkd3d_shader_message_context *message_context;
const struct vsir_program *program;
size_t instruction_idx;
- struct vkd3d_shader_location null_location;
+ struct vkd3d_shader_location location;
bool invalid_instruction_idx;
enum vkd3d_result status;
bool dcl_temps_found;
@@ -9024,13 +9286,12 @@ static void VKD3D_PRINTF_FUNC(3, 4) validator_error(struct validation_context *c
if (ctx->invalid_instruction_idx)
{
- vkd3d_shader_error(ctx->message_context, &ctx->null_location, error, "%s", buf.buffer);
+ vkd3d_shader_error(ctx->message_context, &ctx->location, error, "%s", buf.buffer);
WARN("VSIR validation error: %s\n", buf.buffer);
}
else
{
- const struct vkd3d_shader_instruction *ins = &ctx->program->instructions.elements[ctx->instruction_idx];
- vkd3d_shader_error(ctx->message_context, &ins->location, error,
+ vkd3d_shader_error(ctx->message_context, &ctx->location, error,
"instruction %zu: %s", ctx->instruction_idx + 1, buf.buffer);
WARN("VSIR validation error: instruction %zu: %s\n", ctx->instruction_idx + 1, buf.buffer);
}
@@ -9459,7 +9720,8 @@ static void vsir_validate_label_register(struct validation_context *ctx,
if (reg->data_type != VSIR_DATA_UNUSED)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for a LABEL register.", reg->data_type);
+ "Invalid data type \"%s\" (%#x) for a LABEL register.",
+ vsir_data_type_get_name(reg->data_type, "<unknown>"), reg->data_type);
if (reg->dimension != VSIR_DIMENSION_NONE)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DIMENSION,
@@ -9538,7 +9800,8 @@ static void vsir_validate_sampler_register(struct validation_context *ctx,
if (reg->data_type != VSIR_DATA_UNUSED)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for a SAMPLER register.", reg->data_type);
+ "Invalid data type \"%s\" (%#x) for a SAMPLER register.",
+ vsir_data_type_get_name(reg->data_type, "<unknown>"), reg->data_type);
/* VEC4 is allowed in gather operations. */
if (reg->dimension == VSIR_DIMENSION_SCALAR)
@@ -9564,7 +9827,8 @@ static void vsir_validate_resource_register(struct validation_context *ctx,
if (reg->data_type != VSIR_DATA_UNUSED)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for a RESOURCE register.", reg->data_type);
+ "Invalid data type \"%s\" (%#x) for a RESOURCE register.",
+ vsir_data_type_get_name(reg->data_type, "<unknown>"), reg->data_type);
if (reg->dimension != VSIR_DIMENSION_VEC4)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DIMENSION,
@@ -9590,8 +9854,8 @@ static void vsir_validate_uav_register(struct validation_context *ctx,
if (reg->data_type != VSIR_DATA_UNUSED)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for a UAV register.",
- reg->data_type);
+ "Invalid data type \"%s\" (%#x) for a UAV register.",
+ vsir_data_type_get_name(reg->data_type, "<unknown>"), reg->data_type);
/* NONE is allowed in counter operations. */
if (reg->dimension == VSIR_DIMENSION_SCALAR)
@@ -9663,9 +9927,10 @@ static void vsir_validate_ssa_register(struct validation_context *ctx,
if (data_type_is_64_bit(data->data_type) != data_type_is_64_bit(reg->data_type))
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for a SSA register: "
- "it has already been seen with data type %#x at instruction %zu.",
- reg->data_type, data->data_type, data->first_seen);
+ "Invalid data type \"%s\" (%#x) for SSA register %u: "
+ "it has already been seen with data type \"%s\" (%#x) at instruction %zu.",
+ vsir_data_type_get_name(reg->data_type, "<unknown>"), reg->data_type, reg->idx[0].offset,
+ vsir_data_type_get_name(data->data_type, "<unknown>"), data->data_type, data->first_seen);
}
}
@@ -9913,7 +10178,8 @@ static void vsir_validate_dst_param(struct validation_context *ctx,
default:
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for destination with saturate modifier.", dst->reg.data_type);
+ "Invalid data type \"%s\" (%#x) for destination with saturate modifier.",
+ vsir_data_type_get_name(dst->reg.data_type, "<unknown>"), dst->reg.data_type);
break;
}
@@ -9932,7 +10198,8 @@ static void vsir_validate_dst_param(struct validation_context *ctx,
case 15:
if (dst->reg.data_type != VSIR_DATA_F32)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for destination with shift.", dst->reg.data_type);
+ "Invalid data type \"%s\" (%#x) for destination with shift.",
+ vsir_data_type_get_name(dst->reg.data_type, "<unknown>"), dst->reg.data_type);
break;
default:
@@ -10070,7 +10337,8 @@ static void vsir_validate_src_param(struct validation_context *ctx,
{
if (!(src_modifier_data[src->modifiers].data_type_mask & (1u << src->reg.data_type)))
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_MODIFIERS,
- "Source has invalid modifier %#x for data type %u.", src->modifiers, src->reg.data_type);
+ "Source has invalid modifier %#x for data type \"%s\" (%#x).",
+ src->modifiers, vsir_data_type_get_name(src->reg.data_type, "<unknown>"), src->reg.data_type);
}
switch (src->reg.type)
@@ -10722,7 +10990,7 @@ static void vsir_validate_hull_shader_phase(struct validation_context *ctx,
static void vsir_validate_elementwise_operation(struct validation_context *ctx,
const struct vkd3d_shader_instruction *instruction, const bool types[VSIR_DATA_TYPE_COUNT])
{
- enum vsir_data_type dst_data_type;
+ enum vsir_data_type dst_data_type, src_data_type;
unsigned int i;
if (instruction->dst_count < 1)
@@ -10735,16 +11003,18 @@ static void vsir_validate_elementwise_operation(struct validation_context *ctx,
if (!types[dst_data_type])
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for elementwise operation \"%s\" (%#x).",
- dst_data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid data type \"%s\" (%#x) for elementwise operation \"%s\" (%#x).",
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
for (i = 0; i < instruction->src_count; ++i)
{
- if (instruction->src[i].reg.data_type != dst_data_type)
+ if ((src_data_type = instruction->src[i].reg.data_type) != dst_data_type)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Data type %#x for operand %u doesn't match the destination data type %#x "
+ "Data type \"%s\" (%#x) for operand %u doesn't match the destination data type \"%s\" (%#x) "
"for elementwise operation \"%s\" (%#x).",
- instruction->src[i].reg.data_type, i, dst_data_type,
+ vsir_data_type_get_name(src_data_type, "<unknown>"), src_data_type, i,
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
}
}
@@ -10801,7 +11071,7 @@ static void vsir_validate_logic_elementwise_operation(struct validation_context
static void vsir_validate_comparison_operation(struct validation_context *ctx,
const struct vkd3d_shader_instruction *instruction, const bool types[VSIR_DATA_TYPE_COUNT])
{
- enum vsir_data_type dst_data_type, src_data_type;
+ enum vsir_data_type dst_data_type, src_data_type, data_type;
unsigned int i;
if (instruction->dst_count < 1)
@@ -10811,8 +11081,9 @@ static void vsir_validate_comparison_operation(struct validation_context *ctx,
if (dst_data_type != VSIR_DATA_U32 && dst_data_type != VSIR_DATA_BOOL)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for result of comparison operation \"%s\" (%#x).",
- dst_data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid data type \"%s\" (%#x) for result of comparison operation \"%s\" (%#x).",
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
if (instruction->src_count == 0)
return;
@@ -10824,16 +11095,18 @@ static void vsir_validate_comparison_operation(struct validation_context *ctx,
if (!types[src_data_type])
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid data type %#x for comparison operation \"%s\" (%#x).",
- src_data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid data type \"%s\" (%#x) for comparison operation \"%s\" (%#x).",
+ vsir_data_type_get_name(src_data_type, "<unknown>"), src_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
for (i = 1; i < instruction->src_count; ++i)
{
- if (instruction->src[i].reg.data_type != src_data_type)
+ if ((data_type = instruction->src[i].reg.data_type) != src_data_type)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Data type %#x for operand %u doesn't match the first operands data type %#x "
- "for comparison operation \"%s\" (%#x).",
- instruction->src[i].reg.data_type, i, src_data_type,
+ "Data type \"%s\" (%#x) for operand %u doesn't match the first "
+ "operands data type \"%s\" (%#x) for comparison operation \"%s\" (%#x).",
+ vsir_data_type_get_name(data_type, "<unknown>"), data_type, i,
+ vsir_data_type_get_name(src_data_type, "<unknown>"), src_data_type,
vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
}
}
@@ -10891,19 +11164,21 @@ static void vsir_validate_cast_operation(struct validation_context *ctx,
if (!src_types[src_data_type])
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid source data type %#x for cast operation \"%s\" (%#x).",
- src_data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid source data type \"%s\" (%#x) for cast operation \"%s\" (%#x).",
+ vsir_data_type_get_name(src_data_type, "<unknown>"), src_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
if (!dst_types[dst_data_type])
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid destination data type %#x for cast operation \"%s\" (%#x).",
- dst_data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid destination data type \"%s\" (%#x) for cast operation \"%s\" (%#x).",
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
}
static void vsir_validate_shift_operation(struct validation_context *ctx,
const struct vkd3d_shader_instruction *instruction)
{
- enum vsir_data_type data_type;
+ enum vsir_data_type dst_data_type, src_data_type;
static const bool types[] =
{
@@ -10912,24 +11187,27 @@ static void vsir_validate_shift_operation(struct validation_context *ctx,
[VSIR_DATA_U64] = true,
};
- data_type = instruction->dst[0].reg.data_type;
- if ((size_t)data_type >= ARRAY_SIZE(types) || !types[data_type])
+ dst_data_type = instruction->dst[0].reg.data_type;
+ if ((size_t)dst_data_type >= ARRAY_SIZE(types) || !types[dst_data_type])
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid destination data type %#x for shift operation \"%s\" (%#x).",
- data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid destination data type \"%s\" (%#x) for shift operation \"%s\" (%#x).",
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
- if (instruction->src[0].reg.data_type != data_type)
+ if ((src_data_type = instruction->src[0].reg.data_type) != dst_data_type)
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Data type %#x for source operand 0 doesn't match destination data type %#x "
+ "Data type \"%s\" (%#x) for source operand 0 doesn't match destination data type \"%s\" (%#x) "
"for shift operation \"%s\" (%#x).",
- instruction->src[0].reg.data_type, data_type,
+ vsir_data_type_get_name(src_data_type, "<unknown>"), src_data_type,
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
- data_type = instruction->src[1].reg.data_type;
- if ((size_t)data_type >= ARRAY_SIZE(types) || !types[data_type])
+ src_data_type = instruction->src[1].reg.data_type;
+ if ((size_t)src_data_type >= ARRAY_SIZE(types) || !types[src_data_type])
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid source operand 1 data type %#x for shift operation \"%s\" (%#x).",
- data_type, vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
+ "Invalid source operand 1 data type \"%s\" (%#x) for shift operation \"%s\" (%#x).",
+ vsir_data_type_get_name(src_data_type, "<unknown>"), src_data_type,
+ vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode);
}
static void vsir_validate_branch(struct validation_context *ctx, const struct vkd3d_shader_instruction *instruction)
@@ -11624,7 +11902,8 @@ static void vsir_validate_throw_invalid_dst_type_error_with_flags(struct validat
enum vsir_data_type dst_data_type = instruction->dst[0].reg.data_type;
validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE,
- "Invalid destination data type %#x for operation \"%s\" (%#x) with flags %#x.", dst_data_type,
+ "Invalid destination data type \"%s\" (%#x) for operation \"%s\" (%#x) with flags %#x.",
+ vsir_data_type_get_name(dst_data_type, "<unknown>"), dst_data_type,
vsir_opcode_get_name(instruction->opcode, "<unknown>"), instruction->opcode, instruction->flags);
}
@@ -11842,14 +12121,12 @@ static const struct vsir_validator_instruction_desc vsir_validator_instructions[
[VSIR_OP_SWITCH_MONOLITHIC] = {0, ~0u, vsir_validate_switch_monolithic},
};
-static void vsir_validate_instruction(struct validation_context *ctx)
+static void vsir_validate_instruction(struct validation_context *ctx,
+ const struct vkd3d_shader_instruction *instruction)
{
const struct vkd3d_shader_version *version = &ctx->program->shader_version;
- const struct vkd3d_shader_instruction *instruction;
size_t i;
- instruction = &ctx->program->instructions.elements[ctx->instruction_idx];
-
for (i = 0; i < instruction->dst_count; ++i)
vsir_validate_dst_param(ctx, &instruction->dst[i]);
@@ -11927,7 +12204,7 @@ enum vkd3d_result vsir_program_validate(struct vsir_program *program, uint64_t c
{
.message_context = message_context,
.program = program,
- .null_location = {.source_name = source_name},
+ .location = {.source_name = source_name},
.status = VKD3D_OK,
.phase = VSIR_OP_INVALID,
.invalid_instruction_idx = true,
@@ -11938,6 +12215,8 @@ enum vkd3d_result vsir_program_validate(struct vsir_program *program, uint64_t c
.inner_tess_idxs[0] = ~0u,
.inner_tess_idxs[1] = ~0u,
};
+ struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
+ struct vkd3d_shader_instruction *ins;
unsigned int i;
if (!(config_flags & VKD3D_SHADER_CONFIG_FLAG_FORCE_VALIDATION))
@@ -12046,11 +12325,17 @@ enum vkd3d_result vsir_program_validate(struct vsir_program *program, uint64_t c
ctx.invalid_instruction_idx = false;
- for (ctx.instruction_idx = 0; ctx.instruction_idx < program->instructions.count
- && ctx.status != VKD3D_ERROR_OUT_OF_MEMORY; ++ctx.instruction_idx)
- vsir_validate_instruction(&ctx);
+ ctx.instruction_idx = 0;
+ for (ins = vsir_program_iterator_head(&it); ins && ctx.status != VKD3D_ERROR_OUT_OF_MEMORY;
+ ins = vsir_program_iterator_next(&it))
+ {
+ ctx.location = ins->location;
+ vsir_validate_instruction(&ctx, ins);
+ ++ctx.instruction_idx;
+ }
ctx.invalid_instruction_idx = true;
+ ctx.location = (struct vkd3d_shader_location){.source_name = source_name};
if (ctx.depth != 0)
validator_error(&ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_CONTROL_FLOW, "%zu nested blocks were not closed.", ctx.depth);
@@ -12113,14 +12398,9 @@ static void vsir_transform_(
enum vkd3d_result vsir_program_transform_early(struct vsir_program *program, uint64_t config_flags,
const struct vkd3d_shader_compile_info *compile_info, struct vkd3d_shader_message_context *message_context)
{
- struct vsir_transformation_context ctx =
- {
- .result = VKD3D_OK,
- .program = program,
- .config_flags = config_flags,
- .compile_info = compile_info,
- .message_context = message_context,
- };
+ struct vsir_transformation_context ctx;
+
+ vsir_transformation_context_init(&ctx, program, config_flags, compile_info, message_context);
/* For vsir_program_ensure_diffuse(). */
if (program->shader_version.major <= 2)
@@ -12138,15 +12418,9 @@ enum vkd3d_result vsir_program_transform_early(struct vsir_program *program, uin
enum vkd3d_result vsir_program_lower_d3dbc(struct vsir_program *program, uint64_t config_flags,
const struct vkd3d_shader_compile_info *compile_info, struct vkd3d_shader_message_context *message_context)
{
- struct vsir_transformation_context ctx =
- {
- .result = VKD3D_OK,
- .program = program,
- .config_flags = config_flags,
- .compile_info = compile_info,
- .message_context = message_context,
- };
+ struct vsir_transformation_context ctx;
+ vsir_transformation_context_init(&ctx, program, config_flags, compile_info, message_context);
vsir_transform(&ctx, vsir_program_lower_d3dbc_instructions);
if (program->shader_version.major == 1 && program->shader_version.type == VKD3D_SHADER_TYPE_PIXEL)
vsir_transform(&ctx, vsir_program_normalise_ps1_output);
@@ -12160,15 +12434,9 @@ enum vkd3d_result vsir_program_lower_d3dbc(struct vsir_program *program, uint64_
enum vkd3d_result vsir_program_transform(struct vsir_program *program, uint64_t config_flags,
const struct vkd3d_shader_compile_info *compile_info, struct vkd3d_shader_message_context *message_context)
{
- struct vsir_transformation_context ctx =
- {
- .result = VKD3D_OK,
- .program = program,
- .config_flags = config_flags,
- .compile_info = compile_info,
- .message_context = message_context,
- };
+ struct vsir_transformation_context ctx;
+ vsir_transformation_context_init(&ctx, program, config_flags, compile_info, message_context);
vsir_transform(&ctx, vsir_program_lower_instructions);
if (program->shader_version.major >= 6)
diff --git a/libs/vkd3d/libs/vkd3d-shader/msl.c b/libs/vkd3d/libs/vkd3d-shader/msl.c
index c6e048adb20..9150e77e2c6 100644
--- a/libs/vkd3d/libs/vkd3d-shader/msl.c
+++ b/libs/vkd3d/libs/vkd3d-shader/msl.c
@@ -943,8 +943,8 @@ static void msl_print_texel_offset(struct vkd3d_string_buffer *buffer, struct ms
static void msl_ld(struct msl_generator *gen, const struct vkd3d_shader_instruction *ins)
{
+ unsigned int resource_id, resource_idx, resource_space, sample_count;
const struct msl_resource_type_info *resource_type_info;
- unsigned int resource_id, resource_idx, resource_space;
const struct vkd3d_shader_descriptor_info1 *descriptor;
const struct vkd3d_shader_descriptor_binding *binding;
enum vkd3d_shader_resource_type resource_type;
@@ -969,6 +969,7 @@ static void msl_ld(struct msl_generator *gen, const struct vkd3d_shader_instruct
{
resource_type = descriptor->resource_type;
resource_space = descriptor->register_space;
+ sample_count = descriptor->sample_count;
data_type = descriptor->resource_data_type;
}
else
@@ -977,6 +978,7 @@ static void msl_ld(struct msl_generator *gen, const struct vkd3d_shader_instruct
"Internal compiler error: Undeclared resource descriptor %u.", resource_id);
resource_space = 0;
resource_type = VKD3D_SHADER_RESOURCE_TEXTURE_2D;
+ sample_count = 1;
data_type = VSIR_DATA_F32;
}
@@ -988,6 +990,16 @@ static void msl_ld(struct msl_generator *gen, const struct vkd3d_shader_instruct
msl_compiler_error(gen, VKD3D_SHADER_ERROR_MSL_UNSUPPORTED,
"Texel fetches from resource type %#x are not supported.", resource_type);
+ if (sample_count == 1)
+ {
+ /* Similar to the SPIR-V and GLSL targets, we map multi-sample
+ * textures with sample count 1 to their single-sample equivalents. */
+ if (resource_type == VKD3D_SHADER_RESOURCE_TEXTURE_2DMS)
+ resource_type = VKD3D_SHADER_RESOURCE_TEXTURE_2D;
+ else if (resource_type == VKD3D_SHADER_RESOURCE_TEXTURE_2DMSARRAY)
+ resource_type = VKD3D_SHADER_RESOURCE_TEXTURE_2DARRAY;
+ }
+
if (!(resource_type_info = msl_get_resource_type_info(resource_type)))
{
msl_compiler_error(gen, VKD3D_SHADER_ERROR_MSL_INTERNAL,
@@ -1030,6 +1042,10 @@ static void msl_ld(struct msl_generator *gen, const struct vkd3d_shader_instruct
vkd3d_string_buffer_printf(read, ", ");
if (ins->opcode != VSIR_OP_LD2DMS)
msl_print_src_with_type(read, gen, &ins->src[0], VKD3DSP_WRITEMASK_3, VSIR_DATA_U32);
+ else if (sample_count == 1)
+ /* If the resource isn't a true multisample resource, this is the
+ * "lod" parameter instead of the "sample" parameter. */
+ vkd3d_string_buffer_printf(read, "0");
else
msl_print_src_with_type(read, gen, &ins->src[2], VKD3DSP_WRITEMASK_0, VSIR_DATA_U32);
}
@@ -1294,6 +1310,11 @@ static void msl_store_uav_typed(struct msl_generator *gen, const struct vkd3d_sh
data_type = VSIR_DATA_F32;
}
+ if (resource_type == VKD3D_SHADER_RESOURCE_TEXTURE_2DMS
+ || resource_type == VKD3D_SHADER_RESOURCE_TEXTURE_2DMSARRAY)
+ msl_compiler_error(gen, VKD3D_SHADER_ERROR_MSL_UNSUPPORTED,
+ "Storing to resource type %#x is not supported.", resource_type);
+
if (!(resource_type_info = msl_get_resource_type_info(resource_type)))
{
msl_compiler_error(gen, VKD3D_SHADER_ERROR_MSL_INTERNAL,
@@ -1414,6 +1435,12 @@ static void msl_ret(struct msl_generator *gen, const struct vkd3d_shader_instruc
static void msl_dcl_indexable_temp(struct msl_generator *gen, const struct vkd3d_shader_instruction *ins)
{
const char *type = ins->declaration.indexable_temp.component_count == 4 ? "vkd3d_vec4" : "vkd3d_scalar";
+
+ if (ins->declaration.indexable_temp.initialiser)
+ msl_compiler_error(gen, VKD3D_SHADER_ERROR_MSL_INTERNAL,
+ "Internal compiler error: Unhandled initialiser for indexable temporary %u.",
+ ins->declaration.indexable_temp.register_idx);
+
msl_print_indent(gen->buffer, gen->indent);
vkd3d_string_buffer_printf(gen->buffer, "%s x%u[%u];\n", type,
ins->declaration.indexable_temp.register_idx,
@@ -1516,6 +1543,7 @@ static void msl_handle_instruction(struct msl_generator *gen, const struct vkd3d
break;
case VSIR_OP_GEO:
case VSIR_OP_IGE:
+ case VSIR_OP_UGE:
msl_relop(gen, ins, ">=");
break;
case VSIR_OP_IF:
@@ -1995,6 +2023,7 @@ static void msl_generate_entrypoint_epilogue(struct msl_generator *gen)
static void msl_generate_entrypoint(struct msl_generator *gen)
{
enum vkd3d_shader_type type = gen->program->shader_version.type;
+ bool output = true;
switch (type)
{
@@ -2006,13 +2035,21 @@ static void msl_generate_entrypoint(struct msl_generator *gen)
vkd3d_string_buffer_printf(gen->buffer, "[[early_fragment_tests]]\n");
vkd3d_string_buffer_printf(gen->buffer, "fragment ");
break;
+ case VKD3D_SHADER_TYPE_COMPUTE:
+ vkd3d_string_buffer_printf(gen->buffer, "kernel ");
+ output = false;
+ break;
default:
msl_compiler_error(gen, VKD3D_SHADER_ERROR_MSL_INTERNAL,
"Internal compiler error: Unhandled shader type %#x.", type);
return;
}
- vkd3d_string_buffer_printf(gen->buffer, "vkd3d_%s_out shader_entry(\n", gen->prefix);
+ if (output)
+ vkd3d_string_buffer_printf(gen->buffer, "vkd3d_%s_out ", gen->prefix);
+ else
+ vkd3d_string_buffer_printf(gen->buffer, "void ");
+ vkd3d_string_buffer_printf(gen->buffer, "shader_entry(\n");
if (gen->program->descriptors.descriptor_count)
{
@@ -2054,7 +2091,9 @@ static void msl_generate_entrypoint(struct msl_generator *gen)
msl_generate_entrypoint_epilogue(gen);
- vkd3d_string_buffer_printf(gen->buffer, " return output;\n}\n");
+ if (output)
+ vkd3d_string_buffer_printf(gen->buffer, " return output;\n");
+ vkd3d_string_buffer_printf(gen->buffer, "}\n");
}
static int msl_generator_generate(struct msl_generator *gen, struct vkd3d_shader_code *out)
diff --git a/libs/vkd3d/libs/vkd3d-shader/preproc.l b/libs/vkd3d/libs/vkd3d-shader/preproc.l
index a8c0db358bc..f9b1d67ac36 100644
--- a/libs/vkd3d/libs/vkd3d-shader/preproc.l
+++ b/libs/vkd3d/libs/vkd3d-shader/preproc.l
@@ -20,6 +20,7 @@
%{
+#include "preproc.h"
#include "preproc.tab.h"
#undef ERROR /* defined in wingdi.h */
@@ -823,7 +824,6 @@ int preproc_lexer_parse(const struct vkd3d_shader_compile_info *compile_info,
static const struct vkd3d_shader_preprocess_info default_preprocess_info = {0};
struct preproc_ctx ctx = {0};
char *source_name = NULL;
- void *output_code;
unsigned int i;
vkd3d_string_buffer_init(&ctx.buffer);
@@ -900,16 +900,9 @@ int preproc_lexer_parse(const struct vkd3d_shader_compile_info *compile_info,
return VKD3D_ERROR_INVALID_SHADER;
}
- if (!(output_code = vkd3d_malloc(ctx.buffer.content_size)))
- {
- vkd3d_string_buffer_cleanup(&ctx.buffer);
- return VKD3D_ERROR_OUT_OF_MEMORY;
- }
- memcpy(output_code, ctx.buffer.buffer, ctx.buffer.content_size);
- out->size = ctx.buffer.content_size;
- out->code = output_code;
vkd3d_string_buffer_trace(&ctx.buffer);
- vkd3d_string_buffer_cleanup(&ctx.buffer);
+
+ vkd3d_shader_code_from_string_buffer(out, &ctx.buffer);
return VKD3D_OK;
fail:
diff --git a/libs/vkd3d/libs/vkd3d-shader/spirv.c b/libs/vkd3d/libs/vkd3d-shader/spirv.c
index 97c0d0e73a8..8bc851f9c5b 100644
--- a/libs/vkd3d/libs/vkd3d-shader/spirv.c
+++ b/libs/vkd3d/libs/vkd3d-shader/spirv.c
@@ -2518,7 +2518,7 @@ static uint32_t vkd3d_spirv_build_op_glsl_std450_nclamp(struct vkd3d_spirv_build
GLSLstd450NClamp, operands, ARRAY_SIZE(operands));
}
-static uint32_t vkd3d_spirv_get_type_id(struct vkd3d_spirv_builder *builder,
+static uint32_t spirv_get_type_id_for_component_type(struct vkd3d_spirv_builder *builder,
enum vkd3d_shader_component_type component_type, unsigned int component_count)
{
uint32_t scalar_id, type_id;
@@ -2553,8 +2553,9 @@ static uint32_t vkd3d_spirv_get_type_id(struct vkd3d_spirv_builder *builder,
case VKD3D_SHADER_COMPONENT_DOUBLE:
type_id = vkd3d_spirv_get_op_type_float(builder, 64);
break;
+ case VKD3D_SHADER_COMPONENT_INT64:
case VKD3D_SHADER_COMPONENT_UINT64:
- type_id = vkd3d_spirv_get_op_type_int(builder, 64, 0);
+ type_id = vkd3d_spirv_get_op_type_int(builder, 64, component_type == VKD3D_SHADER_COMPONENT_INT64);
break;
default:
FIXME("Unhandled component type %#x.\n", component_type);
@@ -2564,7 +2565,7 @@ static uint32_t vkd3d_spirv_get_type_id(struct vkd3d_spirv_builder *builder,
else
{
VKD3D_ASSERT(component_type != VKD3D_SHADER_COMPONENT_VOID);
- scalar_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ scalar_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
type_id = vkd3d_spirv_get_op_type_vector(builder, scalar_id, component_count);
}
@@ -2573,13 +2574,13 @@ static uint32_t vkd3d_spirv_get_type_id(struct vkd3d_spirv_builder *builder,
return type_id;
}
-static uint32_t vkd3d_spirv_get_type_id_for_data_type(struct vkd3d_spirv_builder *builder,
+static uint32_t spirv_get_type_id(struct vkd3d_spirv_builder *builder,
enum vsir_data_type data_type, unsigned int component_count)
{
enum vkd3d_shader_component_type component_type;
component_type = vkd3d_component_type_from_data_type(data_type);
- return vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ return spirv_get_type_id_for_component_type(builder, component_type, component_count);
}
static void vkd3d_spirv_builder_init(struct vkd3d_spirv_builder *builder,
@@ -3656,7 +3657,7 @@ static uint32_t spirv_compiler_get_constant(struct spirv_compiler *compiler,
unsigned int i;
VKD3D_ASSERT(0 < component_count && component_count <= VKD3D_VEC4_SIZE);
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
switch (component_type)
{
@@ -3683,7 +3684,7 @@ static uint32_t spirv_compiler_get_constant(struct spirv_compiler *compiler,
}
else
{
- scalar_type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ scalar_type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
for (i = 0; i < component_count; ++i)
component_ids[i] = vkd3d_spirv_get_op_constant(builder, scalar_type_id, values[i]);
return vkd3d_spirv_get_op_constant_composite(builder, type_id, component_ids, component_count);
@@ -3698,9 +3699,10 @@ static uint32_t spirv_compiler_get_constant64(struct spirv_compiler *compiler,
unsigned int i;
VKD3D_ASSERT(0 < component_count && component_count <= VKD3D_DVEC2_SIZE);
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
- if (component_type != VKD3D_SHADER_COMPONENT_DOUBLE && component_type != VKD3D_SHADER_COMPONENT_UINT64)
+ if (component_type != VKD3D_SHADER_COMPONENT_DOUBLE && component_type != VKD3D_SHADER_COMPONENT_INT64
+ && component_type != VKD3D_SHADER_COMPONENT_UINT64)
{
FIXME("Unhandled component_type %#x.\n", component_type);
return vkd3d_spirv_get_op_undef(builder, type_id);
@@ -3712,7 +3714,7 @@ static uint32_t spirv_compiler_get_constant64(struct spirv_compiler *compiler,
}
else
{
- scalar_type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ scalar_type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
for (i = 0; i < component_count; ++i)
component_ids[i] = vkd3d_spirv_get_op_constant64(builder, scalar_type_id, values[i]);
return vkd3d_spirv_get_op_constant_composite(builder, type_id, component_ids, component_count);
@@ -3772,9 +3774,7 @@ static uint32_t spirv_compiler_get_type_id_for_reg(struct spirv_compiler *compil
{
struct vkd3d_spirv_builder *builder = &compiler->spirv_builder;
- return vkd3d_spirv_get_type_id(builder,
- vkd3d_component_type_from_data_type(reg->data_type),
- vsir_write_mask_component_count(write_mask));
+ return spirv_get_type_id(builder, reg->data_type, vsir_write_mask_component_count(write_mask));
}
static uint32_t spirv_compiler_get_type_id_for_dst(struct spirv_compiler *compiler,
@@ -3901,7 +3901,7 @@ static uint32_t spirv_compiler_emit_array_variable(struct spirv_compiler *compil
uint32_t type_id, length_id, ptr_type_id;
unsigned int i;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
for (i = 0; i < length_count; ++i)
{
if (!array_lengths[i])
@@ -4000,8 +4000,8 @@ static uint32_t spirv_compiler_emit_spec_constant(struct spirv_compiler *compile
info = get_spec_constant_info(name);
default_value = info ? info->default_value.u : 0;
- scalar_type_id = vkd3d_spirv_get_type_id(builder, vkd3d_component_type_from_data_type(type), 1);
- vector_type_id = vkd3d_spirv_get_type_id(builder, vkd3d_component_type_from_data_type(type), component_count);
+ scalar_type_id = spirv_get_type_id(builder, type, 1);
+ vector_type_id = spirv_get_type_id(builder, type, component_count);
for (unsigned int i = 0; i < component_count; ++i)
{
@@ -4050,7 +4050,7 @@ static uint32_t spirv_compiler_get_buffer_parameter(struct spirv_compiler *compi
unsigned int index = parameter - compiler->program->parameters;
uint32_t type_id, ptr_id, ptr_type_id;
- type_id = vkd3d_spirv_get_type_id(builder, vkd3d_component_type_from_data_type(type), component_count);
+ type_id = spirv_get_type_id(builder, type, component_count);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassUniform, type_id);
ptr_id = vkd3d_spirv_build_op_access_chain1(builder, ptr_type_id,
compiler->spirv_parameter_info[index].buffer_id,
@@ -4114,7 +4114,7 @@ static uint32_t spirv_compiler_emit_construct_vector(struct spirv_compiler *comp
VKD3D_ASSERT(val_component_idx < val_component_count);
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
if (val_component_count == 1)
{
for (i = 0; i < component_count; ++i)
@@ -4147,10 +4147,11 @@ static uint32_t spirv_compiler_emit_register_addressing(struct spirv_compiler *c
addr_id = spirv_compiler_emit_load_src(compiler, reg_index->rel_addr, VKD3DSP_WRITEMASK_0);
if (reg_index->offset)
{
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
- addr_id = vkd3d_spirv_build_op_iadd(builder, type_id,
- addr_id, spirv_compiler_get_constant_uint(compiler, reg_index->offset));
+ type_id = spirv_get_type_id(builder, VSIR_DATA_U32, 1);
+ addr_id = vkd3d_spirv_build_op_iadd(builder, type_id, addr_id,
+ spirv_compiler_get_constant_uint(compiler, reg_index->offset));
}
+
return addr_id;
}
@@ -4296,7 +4297,7 @@ static uint32_t spirv_compiler_get_descriptor_index(struct spirv_compiler *compi
struct vkd3d_spirv_builder *builder = &compiler->spirv_builder;
uint32_t type_id, ptr_type_id, ptr_id, offset_id, index_ids[2];
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_U32, 1);
if (!(offset_id = compiler->descriptor_offset_ids[push_constant_index]))
{
index_ids[0] = compiler->descriptor_offsets_member_id;
@@ -4369,7 +4370,7 @@ static void spirv_compiler_emit_dereference_register(struct spirv_compiler *comp
if (index_count)
{
component_count = vsir_write_mask_component_count(register_info->write_mask);
- type_id = vkd3d_spirv_get_type_id(builder, register_info->component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, register_info->component_type, component_count);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, register_info->storage_class, type_id);
register_info->id = vkd3d_spirv_build_op_access_chain(builder, ptr_type_id,
register_info->id, indexes, index_count);
@@ -4428,7 +4429,7 @@ static uint32_t spirv_compiler_emit_swizzle(struct spirv_compiler *compiler,
&& (component_count == 1 || vkd3d_swizzle_is_equal(val_write_mask, swizzle, write_mask)))
return val_id;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
if (component_count == 1)
{
@@ -4479,7 +4480,7 @@ static uint32_t spirv_compiler_emit_vector_shuffle(struct spirv_compiler *compil
components[i] = VKD3D_VEC4_SIZE + vsir_swizzle_get_component(swizzle, i);
}
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
return vkd3d_spirv_build_op_vector_shuffle(builder,
type_id, vector1_id, vector2_id, components, component_count);
}
@@ -4494,10 +4495,11 @@ static uint32_t spirv_compiler_emit_int_to_bool(struct spirv_compiler *compiler,
VKD3D_ASSERT(!(condition & ~(VKD3D_SHADER_CONDITIONAL_OP_NZ | VKD3D_SHADER_CONDITIONAL_OP_Z)));
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_BOOL, component_count);
op = condition & VKD3D_SHADER_CONDITIONAL_OP_Z ? SpvOpIEqual : SpvOpINotEqual;
+
return vkd3d_spirv_build_op_tr2(builder, &builder->function_stream, op, type_id, val_id,
- data_type == VSIR_DATA_U64
+ data_type_is_64_bit(data_type)
? spirv_compiler_get_constant_uint64_vector(compiler, 0, component_count)
: spirv_compiler_get_constant_uint_vector(compiler, 0, component_count));
}
@@ -4510,7 +4512,8 @@ static uint32_t spirv_compiler_emit_bool_to_int(struct spirv_compiler *compiler,
true_id = spirv_compiler_get_constant_uint_vector(compiler, signedness ? 0xffffffff : 1, component_count);
false_id = spirv_compiler_get_constant_uint_vector(compiler, 0, component_count);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, component_count);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_U32, component_count);
+
return vkd3d_spirv_build_op_select(builder, type_id, val_id, true_id, false_id);
}
@@ -4523,7 +4526,8 @@ static uint32_t spirv_compiler_emit_bool_to_int64(struct spirv_compiler *compile
true_id = spirv_compiler_get_constant_uint64_vector(compiler, signedness ? UINT64_MAX : 1,
component_count);
false_id = spirv_compiler_get_constant_uint64_vector(compiler, 0, component_count);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT64, component_count);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_U64, component_count);
+
return vkd3d_spirv_build_op_select(builder, type_id, val_id, true_id, false_id);
}
@@ -4535,7 +4539,8 @@ static uint32_t spirv_compiler_emit_bool_to_float(struct spirv_compiler *compile
true_id = spirv_compiler_get_constant_float_vector(compiler, signedness ? -1.0f : 1.0f, component_count);
false_id = spirv_compiler_get_constant_float_vector(compiler, 0.0f, component_count);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, component_count);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_F32, component_count);
+
return vkd3d_spirv_build_op_select(builder, type_id, val_id, true_id, false_id);
}
@@ -4547,7 +4552,8 @@ static uint32_t spirv_compiler_emit_bool_to_double(struct spirv_compiler *compil
true_id = spirv_compiler_get_constant_double_vector(compiler, signedness ? -1.0 : 1.0, component_count);
false_id = spirv_compiler_get_constant_double_vector(compiler, 0.0, component_count);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_DOUBLE, component_count);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_F64, component_count);
+
return vkd3d_spirv_build_op_select(builder, type_id, val_id, true_id, false_id);
}
@@ -4614,7 +4620,8 @@ static uint32_t spirv_compiler_emit_load_undef(struct spirv_compiler *compiler,
VKD3D_ASSERT(reg->type == VKD3DSPR_UNDEF);
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, reg->data_type, component_count);
+ type_id = spirv_get_type_id(builder, reg->data_type, component_count);
+
return vkd3d_spirv_get_op_undef(builder, type_id);
}
@@ -4646,7 +4653,7 @@ static uint32_t spirv_compiler_emit_load_scalar(struct spirv_compiler *compiler,
component_idx, reg->type, reg->idx[0].offset, reg_info->write_mask);
}
- type_id = vkd3d_spirv_get_type_id(builder, reg_info->component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, reg_info->component_type, 1);
reg_id = reg_info->id;
if (reg_component_count != 1)
{
@@ -4663,7 +4670,7 @@ static uint32_t spirv_compiler_emit_load_scalar(struct spirv_compiler *compiler,
{
if (reg_info->component_type != VKD3D_SHADER_COMPONENT_UINT)
{
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id);
}
val_id = spirv_compiler_emit_int_to_bool(compiler,
@@ -4671,7 +4678,7 @@ static uint32_t spirv_compiler_emit_load_scalar(struct spirv_compiler *compiler,
}
else
{
- type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id);
}
}
@@ -4691,7 +4698,7 @@ static uint32_t spirv_compiler_emit_constant_array(struct spirv_compiler *compil
component_type = vkd3d_component_type_from_data_type(icb->data_type);
component_count = icb->component_count;
- elem_type_id = vkd3d_spirv_get_type_id_for_data_type(builder, icb->data_type, component_count);
+ elem_type_id = spirv_get_type_id(builder, icb->data_type, component_count);
length_id = spirv_compiler_get_constant_uint(compiler, element_count);
type_id = vkd3d_spirv_get_op_type_array(builder, elem_type_id, length_id);
@@ -4722,6 +4729,7 @@ static uint32_t spirv_compiler_emit_constant_array(struct spirv_compiler *compil
&icb->data[component_count * i]);
break;
case VSIR_DATA_F64:
+ case VSIR_DATA_I64:
case VSIR_DATA_U64:
{
uint64_t *data = (uint64_t *)icb->data;
@@ -4777,7 +4785,7 @@ static uint32_t spirv_compiler_emit_load_reg(struct spirv_compiler *compiler,
if (!spirv_compiler_get_register_info(compiler, reg, &reg_info))
{
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
return vkd3d_spirv_get_op_undef(builder, type_id);
}
spirv_compiler_emit_dereference_register(compiler, reg, &reg_info);
@@ -4796,7 +4804,7 @@ static uint32_t spirv_compiler_emit_load_reg(struct spirv_compiler *compiler,
}
else
{
- type_id = vkd3d_spirv_get_type_id(builder,
+ type_id = spirv_get_type_id_for_component_type(builder,
reg_info.component_type, vsir_write_mask_component_count(reg_info.write_mask));
val_id = vkd3d_spirv_build_op_load(builder, type_id, reg_info.id, SpvMemoryAccessMaskNone);
swizzle = data_type_is_64_bit(reg->data_type) ? vsir_swizzle_32_from_64(swizzle) : swizzle;
@@ -4811,7 +4819,7 @@ static uint32_t spirv_compiler_emit_load_reg(struct spirv_compiler *compiler,
{
if (reg_info.component_type != VKD3D_SHADER_COMPONENT_UINT)
{
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, component_count);
val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id);
}
val_id = spirv_compiler_emit_int_to_bool(compiler,
@@ -4819,7 +4827,7 @@ static uint32_t spirv_compiler_emit_load_reg(struct spirv_compiler *compiler,
}
else
{
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id);
}
}
@@ -4923,7 +4931,7 @@ static void spirv_compiler_emit_store_scalar(struct spirv_compiler *compiler,
if (vsir_write_mask_component_count(dst_write_mask) > 1)
{
- type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, storage_class, type_id);
component_idx = vsir_write_mask_get_component_idx(write_mask);
component_idx -= vsir_write_mask_get_component_idx(dst_write_mask);
@@ -4951,7 +4959,7 @@ static void spirv_compiler_emit_store(struct spirv_compiler *compiler,
if (dst_component_count == 1 && component_count != 1)
{
- type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
val_id = vkd3d_spirv_build_op_composite_extract1(builder, type_id, val_id,
vsir_write_mask_get_component_idx(dst_write_mask));
write_mask &= dst_write_mask;
@@ -4966,7 +4974,7 @@ static void spirv_compiler_emit_store(struct spirv_compiler *compiler,
if (dst_component_count != component_count)
{
- type_id = vkd3d_spirv_get_type_id(builder, component_type, dst_component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, dst_component_count);
dst_val_id = vkd3d_spirv_build_op_load(builder, type_id, dst_id, SpvMemoryAccessMaskNone);
VKD3D_ASSERT(component_count <= ARRAY_SIZE(components));
@@ -5018,7 +5026,7 @@ static void spirv_compiler_emit_store_reg(struct spirv_compiler *compiler,
if (component_type == VKD3D_SHADER_COMPONENT_BOOL)
val_id = spirv_compiler_emit_bool_to_int(compiler,
vsir_write_mask_component_count(src_write_mask), val_id, false);
- type_id = vkd3d_spirv_get_type_id(builder, reg_info.component_type,
+ type_id = spirv_get_type_id_for_component_type(builder, reg_info.component_type,
vsir_write_mask_component_count(src_write_mask));
val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id);
component_type = reg_info.component_type;
@@ -5101,7 +5109,7 @@ static void spirv_compiler_emit_store_dst_components(struct spirv_compiler *comp
struct vkd3d_spirv_builder *builder = &compiler->spirv_builder;
uint32_t type_id, dst_type_id, val_id;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, component_count);
if (component_count > 1)
{
val_id = vkd3d_spirv_build_op_composite_construct(builder,
@@ -5112,7 +5120,7 @@ static void spirv_compiler_emit_store_dst_components(struct spirv_compiler *comp
val_id = *component_ids;
}
- dst_type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type, component_count);
+ dst_type_id = spirv_get_type_id(builder, dst->reg.data_type, component_count);
if (dst_type_id != type_id)
val_id = vkd3d_spirv_build_op_bitcast(builder, dst_type_id, val_id);
@@ -5281,9 +5289,8 @@ static uint32_t spirv_compiler_emit_draw_parameter_fixup(struct spirv_compiler *
vkd3d_spirv_add_iface_variable(builder, base_var_id);
spirv_compiler_decorate_builtin(compiler, base_var_id, base);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_INT, 1);
- base_id = vkd3d_spirv_build_op_load(builder,
- type_id, base_var_id, SpvMemoryAccessMaskNone);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_I32, 1);
+ base_id = vkd3d_spirv_build_op_load(builder, type_id, base_var_id, SpvMemoryAccessMaskNone);
return vkd3d_spirv_build_op_isub(builder, type_id, index_id, base_id);
}
@@ -5311,17 +5318,16 @@ static uint32_t sv_front_face_fixup(struct spirv_compiler *compiler,
}
/* frag_coord.w = 1.0f / frag_coord.w */
-static uint32_t frag_coord_fixup(struct spirv_compiler *compiler,
- uint32_t frag_coord_id)
+static uint32_t frag_coord_fixup(struct spirv_compiler *compiler, uint32_t frag_coord_id)
{
struct vkd3d_spirv_builder *builder = &compiler->spirv_builder;
uint32_t type_id, w_id;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 1);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_F32, 1);
w_id = vkd3d_spirv_build_op_composite_extract1(builder, type_id, frag_coord_id, 3);
- w_id = vkd3d_spirv_build_op_fdiv(builder, type_id,
- spirv_compiler_get_constant_float(compiler, 1.0f), w_id);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE);
+ w_id = vkd3d_spirv_build_op_fdiv(builder, type_id, spirv_compiler_get_constant_float(compiler, 1.0f), w_id);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_F32, VKD3D_VEC4_SIZE);
+
return vkd3d_spirv_build_op_composite_insert1(builder, type_id, w_id, frag_coord_id, 3);
}
@@ -5527,7 +5533,8 @@ static uint32_t spirv_compiler_emit_load_invocation_id(struct spirv_compiler *co
uint32_t type_id, id;
id = spirv_compiler_get_invocation_id(compiler);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_INT, 1);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_I32, 1);
+
return vkd3d_spirv_build_op_load(builder, type_id, id, SpvMemoryAccessMaskNone);
}
@@ -5867,7 +5874,7 @@ static void spirv_compiler_emit_input(struct spirv_compiler *compiler,
vsir_register_init(&dst_reg, reg_type, VSIR_DATA_F32, 1);
dst_reg.idx[0].offset = element_idx;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, input_component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, input_component_count);
val_id = vkd3d_spirv_build_op_load(builder, type_id, input_id, SpvMemoryAccessMaskNone);
@@ -5876,7 +5883,8 @@ static void spirv_compiler_emit_input(struct spirv_compiler *compiler,
if (component_type != VKD3D_SHADER_COMPONENT_FLOAT)
{
- float_type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, input_component_count);
+ float_type_id = spirv_get_type_id_for_component_type(builder,
+ VKD3D_SHADER_COMPONENT_FLOAT, input_component_count);
val_id = vkd3d_spirv_build_op_bitcast(builder, float_type_id, val_id);
}
@@ -6225,7 +6233,7 @@ static void spirv_compiler_emit_store_shader_output(struct spirv_compiler *compi
if (output_info->component_type != VKD3D_SHADER_COMPONENT_FLOAT)
{
- type_id = vkd3d_spirv_get_type_id(builder, output_info->component_type, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, output_info->component_type, VKD3D_VEC4_SIZE);
val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id);
}
@@ -6250,7 +6258,7 @@ static void spirv_compiler_emit_store_shader_output(struct spirv_compiler *compi
output_id = output_info->id;
if (output_index_id)
{
- type_id = vkd3d_spirv_get_type_id(builder,
+ type_id = spirv_get_type_id_for_component_type(builder,
output_info->component_type, vsir_write_mask_component_count(dst_write_mask));
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassOutput, type_id);
output_id = vkd3d_spirv_build_op_access_chain1(builder, ptr_type_id, output_id, output_index_id);
@@ -6263,7 +6271,7 @@ static void spirv_compiler_emit_store_shader_output(struct spirv_compiler *compi
return;
}
- type_id = vkd3d_spirv_get_type_id(builder, output_info->component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, output_info->component_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassOutput, type_id);
mask = output_info->array_element_mask;
array_idx = spirv_compiler_get_output_array_index(compiler, output);
@@ -6305,7 +6313,7 @@ static void spirv_compiler_emit_shader_epilogue_function(struct spirv_compiler *
function_id = compiler->epilogue_function_id;
void_id = vkd3d_spirv_get_op_type_void(builder);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 4);
+ type_id = spirv_get_type_id(builder, VSIR_DATA_F32, 4);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassPrivate, type_id);
for (i = 0, count = 0; i < ARRAY_SIZE(compiler->private_output_variable); ++i)
{
@@ -6536,7 +6544,7 @@ static void spirv_compiler_emit_dcl_indexable_temp(struct spirv_compiler *compil
vkd3d_spirv_begin_function_stream_insertion(builder, function_location);
component_type = vkd3d_component_type_from_data_type(temp->data_type);
- type_id = vkd3d_spirv_get_type_id(builder, component_type, temp->component_count);
+ type_id = spirv_get_type_id(builder, temp->data_type, temp->component_count);
length_id = spirv_compiler_get_constant_uint(compiler, temp->register_size);
type_id = vkd3d_spirv_get_op_type_array(builder, type_id, length_id);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, storage_class, type_id);
@@ -6577,7 +6585,7 @@ static void spirv_compiler_emit_push_constant_buffers(struct spirv_compiler *com
if (!(member_ids = vkd3d_calloc(count, sizeof(*member_ids))))
return;
- vec4_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE);
+ vec4_id = spirv_get_type_id(builder, VSIR_DATA_F32, VKD3D_VEC4_SIZE);
for (i = 0, j = 0; i < compiler->shader_interface.push_constant_buffer_count; ++i)
{
@@ -6594,7 +6602,7 @@ static void spirv_compiler_emit_push_constant_buffers(struct spirv_compiler *com
if (compiler->offset_info.descriptor_table_count)
{
- uint32_t type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ uint32_t type_id = spirv_get_type_id(builder, VSIR_DATA_U32, 1);
length_id = spirv_compiler_get_constant_uint(compiler, compiler->offset_info.descriptor_table_count);
member_ids[j] = vkd3d_spirv_build_op_type_array(builder, type_id, length_id);
vkd3d_spirv_build_op_decorate1(builder, member_ids[j], SpvDecorationArrayStride, 4);
@@ -6788,7 +6796,7 @@ static void spirv_compiler_emit_cbv_declaration(struct spirv_compiler *compiler,
return;
}
- vec4_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE);
+ vec4_id = spirv_get_type_id(builder, VSIR_DATA_F32, VKD3D_VEC4_SIZE);
length_id = spirv_compiler_get_constant_uint(compiler, size);
array_type_id = vkd3d_spirv_build_op_type_array(builder, vec4_id, length_id);
vkd3d_spirv_build_op_decorate1(builder, array_type_id, SpvDecorationArrayStride, 16);
@@ -6927,7 +6935,7 @@ static uint32_t spirv_compiler_get_image_type_id(struct spirv_compiler *compiler
vkd3d_spirv_enable_capability(builder, SpvCapabilityStorageImageReadWithoutFormat);
}
- sampled_type_id = vkd3d_spirv_get_type_id(builder, data_type, 1);
+ sampled_type_id = spirv_get_type_id_for_component_type(builder, data_type, 1);
return vkd3d_spirv_get_op_type_image(builder, sampled_type_id, resource_type_info->dim,
2, resource_type_info->arrayed, resource_type_info->ms,
reg->type == VKD3DSPR_UAV ? 2 : 1, format);
@@ -7053,7 +7061,7 @@ static void spirv_compiler_emit_resource_declaration(struct spirv_compiler *comp
{
uint32_t array_type_id, struct_id;
- type_id = vkd3d_spirv_get_type_id(builder, sampled_type, 1);
+ type_id = spirv_get_type_id(builder, descriptor->resource_data_type, 1);
array_type_id = vkd3d_spirv_get_op_type_runtime_array(builder, type_id);
vkd3d_spirv_build_op_decorate1(builder, array_type_id, SpvDecorationArrayStride, 4);
@@ -7094,7 +7102,7 @@ static void spirv_compiler_emit_resource_declaration(struct spirv_compiler *comp
{
VKD3D_ASSERT(structure_stride); /* counters are valid only for structured buffers */
- counter_type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ counter_type_id = spirv_get_type_id(builder, VSIR_DATA_U32, 1);
if (spirv_compiler_is_opengl_target(compiler))
{
vkd3d_spirv_enable_capability(builder, SpvCapabilityAtomicStorage);
@@ -7158,7 +7166,7 @@ static void spirv_compiler_emit_workgroup_memory(struct spirv_compiler *compiler
if (alignment)
TRACE("Ignoring alignment %u.\n", alignment);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
length_id = spirv_compiler_get_constant_uint(compiler, size);
array_type_id = vkd3d_spirv_get_op_type_array(builder, type_id, length_id);
@@ -7209,10 +7217,9 @@ static void spirv_compiler_emit_output_vertex_count(struct spirv_compiler *compi
SpvExecutionModeOutputVertices, instruction->declaration.count);
}
-static void spirv_compiler_emit_dcl_input_primitive(struct spirv_compiler *compiler,
- const struct vkd3d_shader_instruction *instruction)
+static void spirv_compiler_emit_input_primitive(struct spirv_compiler *compiler)
{
- enum vkd3d_primitive_type primitive_type = instruction->declaration.primitive_type.type;
+ enum vkd3d_primitive_type primitive_type = compiler->program->input_primitive;
SpvExecutionMode mode;
switch (primitive_type)
@@ -7233,7 +7240,8 @@ static void spirv_compiler_emit_dcl_input_primitive(struct spirv_compiler *compi
mode = SpvExecutionModeInputTrianglesAdjacency;
break;
default:
- FIXME("Unhandled primitive type %#x.\n", primitive_type);
+ spirv_compiler_error(compiler, VKD3D_SHADER_ERROR_SPV_NOT_IMPLEMENTED,
+ "Unhandled input primitive type %#x.", primitive_type);
return;
}
@@ -7263,10 +7271,9 @@ static void spirv_compiler_emit_point_size(struct spirv_compiler *compiler)
}
}
-static void spirv_compiler_emit_dcl_output_topology(struct spirv_compiler *compiler,
- const struct vkd3d_shader_instruction *instruction)
+static void spirv_compiler_emit_output_topology(struct spirv_compiler *compiler)
{
- enum vkd3d_primitive_type primitive_type = instruction->declaration.primitive_type.type;
+ enum vkd3d_primitive_type primitive_type = compiler->program->output_topology;
SpvExecutionMode mode;
switch (primitive_type)
@@ -7282,7 +7289,8 @@ static void spirv_compiler_emit_dcl_output_topology(struct spirv_compiler *compi
mode = SpvExecutionModeOutputTriangleStrip;
break;
default:
- ERR("Unexpected primitive type %#x.\n", primitive_type);
+ spirv_compiler_error(compiler, VKD3D_SHADER_ERROR_SPV_NOT_IMPLEMENTED,
+ "Unhandled output topology %#x.", primitive_type);
return;
}
@@ -7624,11 +7632,12 @@ static void spirv_compiler_emit_bool_cast(struct spirv_compiler *compiler,
/* ITOD is not supported. Frontends which emit bool casts must use ITOF for double. */
val_id = spirv_compiler_emit_bool_to_double(compiler, 1, val_id, instruction->opcode == VSIR_OP_ITOF);
}
- else if (dst->reg.data_type == VSIR_DATA_U16 || dst->reg.data_type == VSIR_DATA_U32)
+ else if (dst->reg.data_type == VSIR_DATA_I16 || dst->reg.data_type == VSIR_DATA_I32
+ || dst->reg.data_type == VSIR_DATA_U16 || dst->reg.data_type == VSIR_DATA_U32)
{
val_id = spirv_compiler_emit_bool_to_int(compiler, 1, val_id, instruction->opcode == VSIR_OP_ITOI);
}
- else if (dst->reg.data_type == VSIR_DATA_U64)
+ else if (dst->reg.data_type == VSIR_DATA_I64 || dst->reg.data_type == VSIR_DATA_U64)
{
val_id = spirv_compiler_emit_bool_to_int64(compiler, 1, val_id, instruction->opcode == VSIR_OP_ITOI);
}
@@ -7724,7 +7733,7 @@ static enum vkd3d_result spirv_compiler_emit_alu_instruction(struct spirv_compil
condition_id = spirv_compiler_emit_int_to_bool(compiler,
VKD3D_SHADER_CONDITIONAL_OP_NZ, src[1].reg.data_type, component_count, src_ids[1]);
- if (dst[0].reg.data_type == VSIR_DATA_U64)
+ if (data_type_is_64_bit(dst[0].reg.data_type))
uint_max_id = spirv_compiler_get_constant_uint64_vector(compiler, UINT64_MAX, component_count);
else
uint_max_id = spirv_compiler_get_constant_uint_vector(compiler, UINT_MAX, component_count);
@@ -7839,7 +7848,7 @@ static void spirv_compiler_emit_ext_glsl_instruction(struct spirv_compiler *comp
unsigned int i, component_count;
enum GLSLstd450 glsl_inst;
- if (src[0].reg.data_type == VSIR_DATA_U64 && (instruction->opcode == VSIR_OP_FIRSTBIT_HI
+ if (data_type_is_64_bit(src[0].reg.data_type) && (instruction->opcode == VSIR_OP_FIRSTBIT_HI
|| instruction->opcode == VSIR_OP_FIRSTBIT_LO || instruction->opcode == VSIR_OP_FIRSTBIT_SHI))
{
/* At least some drivers support this anyway, but if validation is enabled it will fail. */
@@ -7878,7 +7887,8 @@ static void spirv_compiler_emit_ext_glsl_instruction(struct spirv_compiler *comp
component_count = vsir_write_mask_component_count(dst->write_mask);
uint_max_id = spirv_compiler_get_constant_uint_vector(compiler, UINT32_MAX, component_count);
condition_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream, SpvOpIEqual,
- vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count), val_id, uint_max_id);
+ spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count),
+ val_id, uint_max_id);
rev_val_id = vkd3d_spirv_build_op_isub(builder, type_id,
spirv_compiler_get_constant_uint_vector(compiler, 31, component_count), val_id);
val_id = vkd3d_spirv_build_op_select(builder, type_id, condition_id, val_id, rev_val_id);
@@ -7928,7 +7938,7 @@ static void spirv_compiler_emit_mov(struct spirv_compiler *compiler,
dst_id = spirv_compiler_get_register_id(compiler, &dst->reg);
src_id = spirv_compiler_get_register_id(compiler, &src->reg);
- type_id = vkd3d_spirv_get_type_id(builder, dst_reg_info.component_type, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, dst_reg_info.component_type, VKD3D_VEC4_SIZE);
val_id = vkd3d_spirv_build_op_load(builder, type_id, src_id, SpvMemoryAccessMaskNone);
dst_val_id = vkd3d_spirv_build_op_load(builder, type_id, dst_id, SpvMemoryAccessMaskNone);
@@ -7957,7 +7967,7 @@ general_implementation:
val_id = spirv_compiler_emit_load_src(compiler, src, write_mask);
if (dst->reg.data_type != src->reg.data_type)
{
- val_id = vkd3d_spirv_build_op_bitcast(builder, vkd3d_spirv_get_type_id_for_data_type(builder,
+ val_id = vkd3d_spirv_build_op_bitcast(builder, spirv_get_type_id(builder,
dst->reg.data_type, vsir_write_mask_component_count(dst->write_mask)), val_id);
}
spirv_compiler_emit_store_dst(compiler, dst, val_id);
@@ -7983,8 +7993,8 @@ static void spirv_compiler_emit_movc(struct spirv_compiler *compiler,
{
if (instruction->opcode == VSIR_OP_CMP)
condition_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream, SpvOpFOrdGreaterThanEqual,
- vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count), condition_id,
- spirv_compiler_get_constant_float_vector(compiler, 0.0f, component_count));
+ spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count),
+ condition_id, spirv_compiler_get_constant_float_vector(compiler, 0.0f, component_count));
else
condition_id = spirv_compiler_emit_int_to_bool(compiler,
VKD3D_SHADER_CONDITIONAL_OP_NZ, src[0].reg.data_type, component_count, condition_id);
@@ -8010,7 +8020,7 @@ static void spirv_compiler_emit_swapc(struct spirv_compiler *compiler,
src2_id = spirv_compiler_emit_load_src(compiler, &src[2], dst->write_mask);
component_count = vsir_write_mask_component_count(dst->write_mask);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, component_count);
condition_id = spirv_compiler_emit_int_to_bool(compiler,
VKD3D_SHADER_CONDITIONAL_OP_NZ, src[0].reg.data_type, component_count, condition_id);
@@ -8046,7 +8056,7 @@ static void spirv_compiler_emit_dot(struct spirv_compiler *compiler,
for (i = 0; i < ARRAY_SIZE(src_ids); ++i)
src_ids[i] = spirv_compiler_emit_load_src(compiler, &src[i], write_mask);
- type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
val_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream,
SpvOpDot, type_id, src_ids[0], src_ids[1]);
@@ -8092,7 +8102,7 @@ static void spirv_compiler_emit_imad(struct spirv_compiler *compiler,
unsigned int i, component_count;
component_count = vsir_write_mask_component_count(dst->write_mask);
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type, component_count);
+ type_id = spirv_get_type_id(builder, dst->reg.data_type, component_count);
for (i = 0; i < ARRAY_SIZE(src_ids); ++i)
src_ids[i] = spirv_compiler_emit_load_src(compiler, &src[i], dst->write_mask);
@@ -8146,7 +8156,7 @@ static void spirv_compiler_emit_ftoi(struct spirv_compiler *compiler,
component_type = vkd3d_component_type_from_data_type(dst->reg.data_type);
int_max_id = spirv_compiler_get_constant_vector(compiler, component_type, component_count, INT_MAX);
- condition_type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
+ condition_type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
condition_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream,
SpvOpFOrdGreaterThanEqual, condition_type_id, val_id, float_max_id);
@@ -8199,7 +8209,7 @@ static void spirv_compiler_emit_ftou(struct spirv_compiler *compiler,
val_id = vkd3d_spirv_build_op_glsl_std450_max(builder, src_type_id, src_id, zero_id);
uint_max_id = spirv_compiler_get_constant_uint_vector(compiler, UINT_MAX, component_count);
- condition_type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
+ condition_type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
condition_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream,
SpvOpFOrdGreaterThanEqual, condition_type_id, val_id, float_max_id);
@@ -8224,7 +8234,7 @@ static void spirv_compiler_emit_dtof(struct spirv_compiler *compiler,
src_id = spirv_compiler_emit_load_src(compiler, src, write_mask);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, component_count);
val_id = vkd3d_spirv_build_op_tr1(builder, &builder->function_stream, SpvOpFConvert, type_id, src_id);
if (instruction->flags & VKD3DSI_PRECISE_XYZW)
vkd3d_spirv_build_op_decorate(builder, val_id, SpvDecorationNoContraction, NULL, 0);
@@ -8248,8 +8258,8 @@ static void spirv_compiler_emit_bitfield_instruction(struct spirv_compiler *comp
VKD3D_ASSERT(2 <= src_count && src_count <= ARRAY_SIZE(src_ids));
component_type = vkd3d_component_type_from_data_type(dst->reg.data_type);
- type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
- size = (src[src_count - 1].reg.data_type == VSIR_DATA_U64) ? 0x40 : 0x20;
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
+ size = data_type_is_64_bit(src[src_count - 1].reg.data_type) ? 0x40 : 0x20;
mask_id = spirv_compiler_get_constant_uint(compiler, size - 1);
size_id = spirv_compiler_get_constant_uint(compiler, size);
@@ -8305,8 +8315,8 @@ static void spirv_compiler_emit_f16tof32(struct spirv_compiler *compiler,
unsigned int i, j;
instr_set_id = vkd3d_spirv_get_glsl_std450_instr_set(builder);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
- scalar_type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
+ scalar_type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, 1);
/* FIXME: Consider a single UnpackHalf2x16 instruction per 2 components. */
VKD3D_ASSERT(dst->write_mask & VKD3DSP_WRITEMASK_ALL);
@@ -8338,8 +8348,8 @@ static void spirv_compiler_emit_f32tof16(struct spirv_compiler *compiler,
unsigned int i, j;
instr_set_id = vkd3d_spirv_get_glsl_std450_instr_set(builder);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
- scalar_type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
+ scalar_type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
zero_id = spirv_compiler_get_constant_float(compiler, 0.0f);
/* FIXME: Consider a single PackHalf2x16 instruction per 2 components. */
@@ -8418,7 +8428,7 @@ static void spirv_compiler_emit_comparison_instruction(struct spirv_compiler *co
src0_id = spirv_compiler_emit_load_src(compiler, &src[0], write_mask);
src1_id = spirv_compiler_emit_load_src(compiler, &src[1], write_mask);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
result_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream,
op, type_id, src0_id, src1_id);
@@ -8470,7 +8480,7 @@ static void spirv_compiler_emit_float_comparison_instruction(struct spirv_compil
src0_id = spirv_compiler_emit_load_src(compiler, &src[0], dst->write_mask);
src1_id = spirv_compiler_emit_load_src(compiler, &src[1], dst->write_mask);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, component_count);
result_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream, op, type_id, src0_id, src1_id);
result_id = spirv_compiler_emit_bool_to_float(compiler, component_count, result_id, false);
@@ -8999,7 +9009,7 @@ static void spirv_compiler_emit_ld(struct spirv_compiler *compiler,
spirv_compiler_prepare_image(compiler, &image, &src[1].reg, NULL, VKD3D_IMAGE_FLAG_NONE);
- type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, VKD3D_VEC4_SIZE);
coordinate_mask = (1u << image.resource_type_info->coordinate_component_count) - 1;
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], coordinate_mask);
if (image.resource_type_info->resource_type != VKD3D_SHADER_RESOURCE_BUFFER && !multisample)
@@ -9045,7 +9055,7 @@ static void spirv_compiler_emit_lod(struct spirv_compiler *compiler,
spirv_compiler_prepare_image(compiler, &image,
&resource->reg, &sampler->reg, VKD3D_IMAGE_FLAG_SAMPLED);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_ALL);
val_id = vkd3d_spirv_build_op_image_query_lod(builder,
type_id, image.sampled_image_id, coordinate_id);
@@ -9115,7 +9125,7 @@ static void spirv_compiler_emit_sample(struct spirv_compiler *compiler,
instruction, image.resource_type_info);
}
- sampled_type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, VKD3D_VEC4_SIZE);
+ sampled_type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, VKD3D_VEC4_SIZE);
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_ALL);
VKD3D_ASSERT(image_operand_count <= ARRAY_SIZE(image_operands));
val_id = vkd3d_spirv_build_op_image_sample(builder, op, sampled_type_id,
@@ -9160,7 +9170,7 @@ static void spirv_compiler_emit_sample_c(struct spirv_compiler *compiler,
instruction, image.resource_type_info);
}
- sampled_type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, 1);
+ sampled_type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, 1);
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_ALL);
dref_id = spirv_compiler_emit_load_src(compiler, &src[3], VKD3DSP_WRITEMASK_0);
val_id = vkd3d_spirv_build_op_image_sample_dref(builder, op, sampled_type_id,
@@ -9219,7 +9229,7 @@ static void spirv_compiler_emit_gather4(struct spirv_compiler *compiler,
instruction, image.resource_type_info);
}
- sampled_type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, VKD3D_VEC4_SIZE);
+ sampled_type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, VKD3D_VEC4_SIZE);
coordinate_mask = (1u << image.resource_type_info->coordinate_component_count) - 1;
coordinate_id = spirv_compiler_emit_load_src(compiler, addr, coordinate_mask);
if (image_flags & VKD3D_IMAGE_FLAG_DEPTH)
@@ -9301,10 +9311,10 @@ static void spirv_compiler_emit_ld_raw_structured_srv_uav(struct spirv_compiler
if (storage_buffer_uav)
{
- texel_type_id = vkd3d_spirv_get_type_id(builder, resource_symbol->info.resource.sampled_type, 1);
+ texel_type_id = spirv_get_type_id_for_component_type(builder, resource_symbol->info.resource.sampled_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassUniform, texel_type_id);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
base_coordinate_id = spirv_compiler_emit_raw_structured_addressing(compiler,
type_id, resource_symbol->info.resource.structure_stride,
&src[0], VKD3DSP_WRITEMASK_0, &src[1], VKD3DSP_WRITEMASK_0);
@@ -9336,11 +9346,11 @@ static void spirv_compiler_emit_ld_raw_structured_srv_uav(struct spirv_compiler
spirv_compiler_prepare_image(compiler, &image, &resource->reg, NULL, VKD3D_IMAGE_FLAG_NONE);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
base_coordinate_id = spirv_compiler_emit_raw_structured_addressing(compiler,
type_id, image.structure_stride, &src[0], VKD3DSP_WRITEMASK_0, &src[1], VKD3DSP_WRITEMASK_0);
- texel_type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, VKD3D_VEC4_SIZE);
+ texel_type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, VKD3D_VEC4_SIZE);
VKD3D_ASSERT(dst->write_mask & VKD3DSP_WRITEMASK_ALL);
for (i = 0, j = 0; i < VKD3D_VEC4_SIZE; ++i)
{
@@ -9379,7 +9389,7 @@ static void spirv_compiler_emit_ld_tgsm(struct spirv_compiler *compiler,
if (!spirv_compiler_get_register_info(compiler, &resource->reg, &reg_info))
return;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, reg_info.storage_class, type_id);
base_coordinate_id = spirv_compiler_emit_raw_structured_addressing(compiler,
type_id, reg_info.structure_stride, &src[0], VKD3DSP_WRITEMASK_0, &src[1], VKD3DSP_WRITEMASK_0);
@@ -9438,10 +9448,10 @@ static void spirv_compiler_emit_store_uav_raw_structured(struct spirv_compiler *
if (spirv_compiler_use_storage_buffer(compiler, &resource_symbol->info.resource))
{
- type_id = vkd3d_spirv_get_type_id(builder, resource_symbol->info.resource.sampled_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, resource_symbol->info.resource.sampled_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassUniform, type_id);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
base_coordinate_id = spirv_compiler_emit_raw_structured_addressing(compiler,
type_id, resource_symbol->info.resource.structure_stride,
&src[0], VKD3DSP_WRITEMASK_0, &src[1], VKD3DSP_WRITEMASK_0);
@@ -9469,7 +9479,7 @@ static void spirv_compiler_emit_store_uav_raw_structured(struct spirv_compiler *
}
else
{
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
spirv_compiler_prepare_image(compiler, &image, &dst->reg, NULL, VKD3D_IMAGE_FLAG_NONE);
base_coordinate_id = spirv_compiler_emit_raw_structured_addressing(compiler,
type_id, image.structure_stride, &src[0], VKD3DSP_WRITEMASK_0, &src[1], VKD3DSP_WRITEMASK_0);
@@ -9512,7 +9522,7 @@ static void spirv_compiler_emit_store_tgsm(struct spirv_compiler *compiler,
if (!spirv_compiler_get_register_info(compiler, &dst->reg, &reg_info))
return;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, reg_info.storage_class, type_id);
base_coordinate_id = spirv_compiler_emit_raw_structured_addressing(compiler,
type_id, reg_info.structure_stride, &src[0], VKD3DSP_WRITEMASK_0, &src[1], VKD3DSP_WRITEMASK_0);
@@ -9570,7 +9580,7 @@ static void spirv_compiler_emit_ld_uav_typed(struct spirv_compiler *compiler,
if (spirv_compiler_use_storage_buffer(compiler, &resource_symbol->info.resource))
{
- type_id = vkd3d_spirv_get_type_id(builder, resource_symbol->info.resource.sampled_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, resource_symbol->info.resource.sampled_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassUniform, type_id);
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_0);
indices[0] = spirv_compiler_get_constant_uint(compiler, 0);
@@ -9585,7 +9595,7 @@ static void spirv_compiler_emit_ld_uav_typed(struct spirv_compiler *compiler,
else
{
spirv_compiler_prepare_image(compiler, &image, &src[1].reg, NULL, VKD3D_IMAGE_FLAG_NONE);
- type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, VKD3D_VEC4_SIZE);
coordinate_mask = (1u << image.resource_type_info->coordinate_component_count) - 1;
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], coordinate_mask);
@@ -9613,7 +9623,7 @@ static void spirv_compiler_emit_store_uav_typed(struct spirv_compiler *compiler,
if (spirv_compiler_use_storage_buffer(compiler, &resource_symbol->info.resource))
{
- type_id = vkd3d_spirv_get_type_id(builder, resource_symbol->info.resource.sampled_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, resource_symbol->info.resource.sampled_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassUniform, type_id);
coordinate_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_0);
indices[0] = spirv_compiler_get_constant_uint(compiler, 0);
@@ -9658,7 +9668,7 @@ static void spirv_compiler_emit_uav_counter_instruction(struct spirv_compiler *c
counter_id = resource_symbol->info.resource.uav_counter_id;
VKD3D_ASSERT(counter_id);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
if (resource_symbol->info.resource.uav_counter_array)
{
@@ -9820,7 +9830,7 @@ static void spirv_compiler_emit_atomic_instruction(struct spirv_compiler *compil
}
}
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
if (structure_stride || raw)
{
VKD3D_ASSERT(!raw != !structure_stride);
@@ -9845,7 +9855,7 @@ static void spirv_compiler_emit_atomic_instruction(struct spirv_compiler *compil
if (spirv_compiler_use_storage_buffer(compiler, &resource_symbol->info.resource))
{
component_type = resource_symbol->info.resource.sampled_type;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassUniform, type_id);
operands[0] = spirv_compiler_get_constant_uint(compiler, 0);
operands[1] = coordinate_id;
@@ -9854,7 +9864,7 @@ static void spirv_compiler_emit_atomic_instruction(struct spirv_compiler *compil
else
{
component_type = image.sampled_type;
- type_id = vkd3d_spirv_get_type_id(builder, image.sampled_type, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, image.sampled_type, 1);
ptr_type_id = vkd3d_spirv_get_op_type_pointer(builder, SpvStorageClassImage, type_id);
sample_id = spirv_compiler_get_constant_uint(compiler, 0);
pointer_id = vkd3d_spirv_build_op_image_texel_pointer(builder,
@@ -9907,7 +9917,7 @@ static void spirv_compiler_emit_bufinfo(struct spirv_compiler *compiler,
{
resource_symbol = spirv_compiler_find_resource(compiler, &src->reg);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
val_id = vkd3d_spirv_build_op_array_length(builder, type_id, resource_symbol->id, 0);
write_mask = VKD3DSP_WRITEMASK_0;
}
@@ -9917,7 +9927,7 @@ static void spirv_compiler_emit_bufinfo(struct spirv_compiler *compiler,
spirv_compiler_prepare_image(compiler, &image, &src->reg, NULL, VKD3D_IMAGE_FLAG_NONE);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
val_id = vkd3d_spirv_build_op_image_query_size(builder, type_id, image.image_id);
write_mask = VKD3DSP_WRITEMASK_0;
}
@@ -9927,7 +9937,7 @@ static void spirv_compiler_emit_bufinfo(struct spirv_compiler *compiler,
stride_id = spirv_compiler_get_constant_uint(compiler, image.structure_stride);
constituents[0] = vkd3d_spirv_build_op_udiv(builder, type_id, val_id, stride_id);
constituents[1] = stride_id;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, ARRAY_SIZE(constituents));
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, ARRAY_SIZE(constituents));
val_id = vkd3d_spirv_build_op_composite_construct(builder,
type_id, constituents, ARRAY_SIZE(constituents));
write_mask |= VKD3DSP_WRITEMASK_1;
@@ -9966,14 +9976,14 @@ static void spirv_compiler_emit_resinfo(struct spirv_compiler *compiler,
size_component_count = image.resource_type_info->coordinate_component_count;
if (image.resource_type_info->dim == SpvDimCube)
--size_component_count;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, size_component_count);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, size_component_count);
supports_mipmaps = src[1].reg.type != VKD3DSPR_UAV && !image.resource_type_info->ms;
if (supports_mipmaps)
{
lod_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_0);
val_id = vkd3d_spirv_build_op_image_query_size_lod(builder, type_id, image.image_id, lod_id);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
miplevel_count_id = vkd3d_spirv_build_op_image_query_levels(builder, type_id, image.image_id);
}
else
@@ -9987,14 +9997,14 @@ static void spirv_compiler_emit_resinfo(struct spirv_compiler *compiler,
for (i = 0; i < 3 - size_component_count; ++i)
constituents[i + 1] = spirv_compiler_get_constant_uint(compiler, 0);
constituents[i + 1] = miplevel_count_id;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE);
val_id = vkd3d_spirv_build_op_composite_construct(builder,
type_id, constituents, i + 2);
if (!(instruction->flags & VKD3DSI_RESINFO_UINT))
{
component_type = VKD3D_SHADER_COMPONENT_FLOAT;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, VKD3D_VEC4_SIZE);
val_id = vkd3d_spirv_build_op_convert_utof(builder, type_id, val_id);
if (instruction->flags & VKD3DSI_PRECISE_XYZW)
vkd3d_spirv_build_op_decorate(builder, val_id, SpvDecorationNoContraction, NULL, 0);
@@ -10022,7 +10032,7 @@ static uint32_t spirv_compiler_emit_query_sample_count(struct spirv_compiler *co
vkd3d_spirv_enable_capability(builder, SpvCapabilityImageQuery);
spirv_compiler_prepare_image(compiler, &image, &src->reg, NULL, VKD3D_IMAGE_FLAG_NONE);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
val_id = vkd3d_spirv_build_op_image_query_samples(builder, type_id, image.image_id);
}
@@ -10049,13 +10059,13 @@ static void spirv_compiler_emit_sample_info(struct spirv_compiler *compiler,
constituents[0] = val_id;
for (i = 1; i < VKD3D_VEC4_SIZE; ++i)
constituents[i] = spirv_compiler_get_constant_uint(compiler, 0);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE);
val_id = vkd3d_spirv_build_op_composite_construct(builder, type_id, constituents, VKD3D_VEC4_SIZE);
if (!(instruction->flags & VKD3DSI_SAMPLE_INFO_UINT))
{
component_type = VKD3D_SHADER_COMPONENT_FLOAT;
- type_id = vkd3d_spirv_get_type_id(builder, component_type, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, component_type, VKD3D_VEC4_SIZE);
val_id = vkd3d_spirv_build_op_convert_utof(builder, type_id, val_id);
if (instruction->flags & VKD3DSI_PRECISE_XYZW)
vkd3d_spirv_build_op_decorate(builder, val_id, SpvDecorationNoContraction, NULL, 0);
@@ -10121,13 +10131,13 @@ static void spirv_compiler_emit_sample_position(struct spirv_compiler *compiler,
sample_count_id = spirv_compiler_emit_query_sample_count(compiler, &instruction->src[0]);
sample_index_id = spirv_compiler_emit_load_src(compiler, &instruction->src[1], VKD3DSP_WRITEMASK_0);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
index_id = vkd3d_spirv_build_op_iadd(builder, type_id, sample_count_id, sample_index_id);
index_id = vkd3d_spirv_build_op_isub(builder,
type_id, index_id, spirv_compiler_get_constant_uint(compiler, 1));
/* Validate sample index. */
- bool_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_BOOL, 1);
+ bool_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_BOOL, 1);
id = vkd3d_spirv_build_op_logical_and(builder, bool_id,
vkd3d_spirv_build_op_uless_than(builder, bool_id, sample_index_id, sample_count_id),
vkd3d_spirv_build_op_uless_than_equal(builder,
@@ -10135,7 +10145,7 @@ static void spirv_compiler_emit_sample_position(struct spirv_compiler *compiler,
index_id = vkd3d_spirv_build_op_select(builder, type_id,
id, index_id, spirv_compiler_get_constant_uint(compiler, 0));
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT, 2);
if (!(id = compiler->sample_positions_id))
{
length_id = spirv_compiler_get_constant_uint(compiler, ARRAY_SIZE(standard_sample_positions));
@@ -10199,7 +10209,7 @@ static void spirv_compiler_emit_eval_attrib(struct spirv_compiler *compiler,
src_ids[src_count++] = spirv_compiler_emit_load_src(compiler, &src[1], VKD3DSP_WRITEMASK_0);
}
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT,
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_FLOAT,
vsir_write_mask_component_count(register_info.write_mask));
instr_set_id = vkd3d_spirv_get_glsl_std450_instr_set(builder);
@@ -10334,9 +10344,8 @@ static void spirv_compiler_emit_quad_read_across(struct spirv_compiler *compiler
const struct vkd3d_shader_src_param *src = instruction->src;
uint32_t type_id, direction_type_id, direction_id, val_id;
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type,
- vsir_write_mask_component_count(dst->write_mask));
- direction_type_id = vkd3d_spirv_get_type_id_for_data_type(builder, VSIR_DATA_U32, 1);
+ type_id = spirv_get_type_id(builder, dst->reg.data_type, vsir_write_mask_component_count(dst->write_mask));
+ direction_type_id = spirv_get_type_id(builder, VSIR_DATA_U32, 1);
val_id = spirv_compiler_emit_load_src(compiler, src, dst->write_mask);
direction_id = map_quad_read_across_direction(instruction->opcode);
direction_id = vkd3d_spirv_get_op_constant(builder, direction_type_id, direction_id);
@@ -10355,14 +10364,12 @@ static void spirv_compiler_emit_quad_read_lane_at(struct spirv_compiler *compile
if (!register_is_constant_or_undef(&src[1].reg))
{
- FIXME("Unsupported non-constant quad read lane index.\n");
spirv_compiler_error(compiler, VKD3D_SHADER_ERROR_SPV_NOT_IMPLEMENTED,
"Non-constant quad read lane indices are not supported.");
return;
}
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type,
- vsir_write_mask_component_count(dst->write_mask));
+ type_id = spirv_get_type_id(builder, dst->reg.data_type, vsir_write_mask_component_count(dst->write_mask));
val_id = spirv_compiler_emit_load_src(compiler, &src[0], dst->write_mask);
lane_id = spirv_compiler_emit_load_src(compiler, &src[1], VKD3DSP_WRITEMASK_0);
val_id = vkd3d_spirv_build_op_group_nonuniform_quad_broadcast(builder, type_id, val_id, lane_id);
@@ -10411,7 +10418,7 @@ static uint32_t spirv_compiler_emit_group_nonuniform_ballot(struct spirv_compile
struct vkd3d_spirv_builder *builder = &compiler->spirv_builder;
uint32_t type_id, val_id;
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE);
val_id = spirv_compiler_emit_load_src(compiler, src, VKD3DSP_WRITEMASK_0);
val_id = vkd3d_spirv_build_op_group_nonuniform_ballot(builder, type_id, val_id);
@@ -10470,8 +10477,7 @@ static void spirv_compiler_emit_wave_alu_op(struct spirv_compiler *compiler,
op = map_wave_alu_op(instruction->opcode, data_type_is_floating_point(src->reg.data_type));
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type,
- vsir_write_mask_component_count(dst->write_mask));
+ type_id = spirv_get_type_id(builder, dst->reg.data_type, vsir_write_mask_component_count(dst->write_mask));
val_id = spirv_compiler_emit_load_src(compiler, &src[0], dst->write_mask);
vkd3d_spirv_enable_capability(builder, SpvCapabilityGroupNonUniformArithmetic);
@@ -10495,7 +10501,7 @@ static void spirv_compiler_emit_wave_bit_count(struct spirv_compiler *compiler,
: SpvGroupOperationReduce;
val_id = spirv_compiler_emit_group_nonuniform_ballot(compiler, instruction->src);
- type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
+ type_id = spirv_get_type_id_for_component_type(builder, VKD3D_SHADER_COMPONENT_UINT, 1);
val_id = vkd3d_spirv_build_op_group_nonuniform_ballot_bit_count(builder, type_id, group_op, val_id);
spirv_compiler_emit_store_dst(compiler, dst, val_id);
@@ -10520,8 +10526,7 @@ static void spirv_compiler_emit_wave_read_lane_at(struct spirv_compiler *compile
const struct vkd3d_shader_src_param *src = instruction->src;
uint32_t type_id, lane_id, val_id;
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type,
- vsir_write_mask_component_count(dst->write_mask));
+ type_id = spirv_get_type_id(builder, dst->reg.data_type, vsir_write_mask_component_count(dst->write_mask));
val_id = spirv_compiler_emit_load_src(compiler, &src[0], dst->write_mask);
lane_id = spirv_compiler_emit_load_src(compiler, &src[1], VKD3DSP_WRITEMASK_0);
@@ -10548,8 +10553,7 @@ static void spirv_compiler_emit_wave_read_lane_first(struct spirv_compiler *comp
const struct vkd3d_shader_src_param *src = instruction->src;
uint32_t type_id, val_id;
- type_id = vkd3d_spirv_get_type_id_for_data_type(builder, dst->reg.data_type,
- vsir_write_mask_component_count(dst->write_mask));
+ type_id = spirv_get_type_id(builder, dst->reg.data_type, vsir_write_mask_component_count(dst->write_mask));
val_id = spirv_compiler_emit_load_src(compiler, src, dst->write_mask);
val_id = vkd3d_spirv_build_op_group_nonuniform_broadcast_first(builder, type_id, val_id);
@@ -10608,12 +10612,6 @@ static int spirv_compiler_handle_instruction(struct spirv_compiler *compiler,
case VSIR_OP_DCL_VERTICES_OUT:
spirv_compiler_emit_output_vertex_count(compiler, instruction);
break;
- case VSIR_OP_DCL_INPUT_PRIMITIVE:
- spirv_compiler_emit_dcl_input_primitive(compiler, instruction);
- break;
- case VSIR_OP_DCL_OUTPUT_TOPOLOGY:
- spirv_compiler_emit_dcl_output_topology(compiler, instruction);
- break;
case VSIR_OP_DCL_GS_INSTANCES:
spirv_compiler_emit_dcl_gs_instances(compiler, instruction);
break;
@@ -11066,7 +11064,14 @@ static int spirv_compiler_generate_spirv(struct spirv_compiler *compiler,
if (program->ssa_count)
spirv_compiler_allocate_ssa_register_ids(compiler, program->ssa_count);
if (compiler->shader_type == VKD3D_SHADER_TYPE_COMPUTE)
+ {
spirv_compiler_emit_thread_group_size(compiler, &program->thread_group_size);
+ }
+ else if (compiler->shader_type == VKD3D_SHADER_TYPE_GEOMETRY)
+ {
+ spirv_compiler_emit_input_primitive(compiler);
+ spirv_compiler_emit_output_topology(compiler);
+ }
spirv_compiler_emit_global_flags(compiler, program->global_flags);
spirv_compiler_emit_descriptor_declarations(compiler);
@@ -11080,7 +11085,7 @@ static int spirv_compiler_generate_spirv(struct spirv_compiler *compiler,
{
uint32_t type_id, struct_id, ptr_type_id, var_id;
- type_id = vkd3d_spirv_get_type_id(builder,
+ type_id = spirv_get_type_id_for_component_type(builder,
vkd3d_component_type_from_data_type(parameter_data_type_map[parameter->data_type].type),
parameter_data_type_map[parameter->data_type].component_count);
diff --git a/libs/vkd3d/libs/vkd3d-shader/tpf.c b/libs/vkd3d/libs/vkd3d-shader/tpf.c
index ea15c1a9ad5..ec1d8b91e09 100644
--- a/libs/vkd3d/libs/vkd3d-shader/tpf.c
+++ b/libs/vkd3d/libs/vkd3d-shader/tpf.c
@@ -665,6 +665,8 @@ struct vkd3d_shader_sm4_parser
{
const uint32_t *start, *end, *ptr;
+ struct vsir_program *program;
+
enum vkd3d_shader_opcode phase;
bool has_control_point_phase;
unsigned int input_register_masks[MAX_REG_OUTPUT];
@@ -764,7 +766,7 @@ static const enum vsir_data_type data_type_table[] =
static bool shader_is_sm_5_1(const struct vkd3d_shader_sm4_parser *sm4)
{
- const struct vkd3d_shader_version *version = &sm4->p.program->shader_version;
+ const struct vkd3d_shader_version *version = &sm4->program->shader_version;
return version->major >= 5 && version->minor >= 1;
}
@@ -849,7 +851,7 @@ static void shader_sm4_read_shader_data(struct vkd3d_shader_instruction *ins, ui
icb->element_count = icb_size / VKD3D_VEC4_SIZE;
icb->is_null = false;
memcpy(icb->data, tokens, sizeof(*tokens) * icb_size);
- shader_instruction_array_add_icb(&priv->p.program->instructions, icb);
+ shader_instruction_array_add_icb(&priv->program->instructions, icb);
ins->declaration.icb = icb;
}
@@ -971,7 +973,7 @@ static void shader_sm4_read_dcl_index_range(struct vkd3d_shader_instruction *ins
uint32_t opcode_token, const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *priv)
{
struct vkd3d_shader_index_range *index_range = &ins->declaration.index_range;
- struct vsir_program *program = priv->p.program;
+ struct vsir_program *program = priv->program;
unsigned int i, register_idx, register_count;
const struct shader_signature *signature;
enum vkd3d_shader_register_type type;
@@ -1094,14 +1096,14 @@ static void shader_sm4_read_dcl_output_topology(struct vkd3d_shader_instruction
if (ins->declaration.primitive_type.type == VKD3D_PT_UNDEFINED)
FIXME("Unhandled output primitive type %#x.\n", primitive_type);
- priv->p.program->output_topology = ins->declaration.primitive_type.type;
+ priv->program->output_topology = ins->declaration.primitive_type.type;
}
static void shader_sm4_read_dcl_input_primitive(struct vkd3d_shader_instruction *ins, uint32_t opcode,
uint32_t opcode_token, const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *sm4)
{
enum vkd3d_sm4_input_primitive_type primitive_type;
- struct vsir_program *program = sm4->p.program;
+ struct vsir_program *program = sm4->program;
primitive_type = (opcode_token & VKD3D_SM4_PRIMITIVE_TYPE_MASK) >> VKD3D_SM4_PRIMITIVE_TYPE_SHIFT;
if (VKD3D_SM5_INPUT_PT_PATCH1 <= primitive_type && primitive_type <= VKD3D_SM5_INPUT_PT_PATCH32)
@@ -1129,7 +1131,7 @@ static void shader_sm4_read_dcl_input_primitive(struct vkd3d_shader_instruction
static void shader_sm4_read_declaration_count(struct vkd3d_shader_instruction *ins, uint32_t opcode,
uint32_t opcode_token, const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *sm4)
{
- struct vsir_program *program = sm4->p.program;
+ struct vsir_program *program = sm4->program;
ins->declaration.count = *tokens;
if (opcode == VKD3D_SM4_OP_DCL_TEMPS)
@@ -1161,7 +1163,7 @@ static void shader_sm4_read_dcl_input_ps(struct vkd3d_shader_instruction *ins, u
if (shader_sm4_read_dst_param(priv, &tokens, &tokens[token_count], VSIR_DATA_F32, dst))
{
struct signature_element *e = vsir_signature_find_element_for_reg(
- &priv->p.program->input_signature, dst->reg.idx[dst->reg.idx_count - 1].offset, dst->write_mask);
+ &priv->program->input_signature, dst->reg.idx[dst->reg.idx_count - 1].offset, dst->write_mask);
if (!e)
{
@@ -1187,7 +1189,7 @@ static void shader_sm4_read_dcl_input_ps_siv(struct vkd3d_shader_instruction *in
if (shader_sm4_read_dst_param(priv, &tokens, &tokens[token_count], VSIR_DATA_F32, dst))
{
struct signature_element *e = vsir_signature_find_element_for_reg(
- &priv->p.program->input_signature, dst->reg.idx[dst->reg.idx_count - 1].offset, dst->write_mask);
+ &priv->program->input_signature, dst->reg.idx[dst->reg.idx_count - 1].offset, dst->write_mask);
if (!e)
{
@@ -1220,7 +1222,7 @@ static void shader_sm4_read_dcl_global_flags(struct vkd3d_shader_instruction *in
uint32_t opcode_token, const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *sm4)
{
ins->declaration.global_flags = (opcode_token & VKD3D_SM4_GLOBAL_FLAGS_MASK) >> VKD3D_SM4_GLOBAL_FLAGS_SHIFT;
- sm4->p.program->global_flags = ins->declaration.global_flags;
+ sm4->program->global_flags = ins->declaration.global_flags;
}
static void shader_sm5_read_fcall(struct vkd3d_shader_instruction *ins, uint32_t opcode, uint32_t opcode_token,
@@ -1256,7 +1258,7 @@ static void shader_sm5_read_dcl_interface(struct vkd3d_shader_instruction *ins,
static void shader_sm5_read_control_point_count(struct vkd3d_shader_instruction *ins, uint32_t opcode,
uint32_t opcode_token, const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *sm4)
{
- struct vsir_program *program = sm4->p.program;
+ struct vsir_program *program = sm4->program;
ins->declaration.count = (opcode_token & VKD3D_SM5_CONTROL_POINT_COUNT_MASK)
>> VKD3D_SM5_CONTROL_POINT_COUNT_SHIFT;
@@ -1272,7 +1274,7 @@ static void shader_sm5_read_dcl_tessellator_domain(struct vkd3d_shader_instructi
{
ins->declaration.tessellator_domain = (opcode_token & VKD3D_SM5_TESSELLATOR_MASK)
>> VKD3D_SM5_TESSELLATOR_SHIFT;
- priv->p.program->tess_domain = ins->declaration.tessellator_domain;
+ priv->program->tess_domain = ins->declaration.tessellator_domain;
}
static void shader_sm5_read_dcl_tessellator_partitioning(struct vkd3d_shader_instruction *ins, uint32_t opcode,
@@ -1280,7 +1282,7 @@ static void shader_sm5_read_dcl_tessellator_partitioning(struct vkd3d_shader_ins
{
ins->declaration.tessellator_partitioning = (opcode_token & VKD3D_SM5_TESSELLATOR_MASK)
>> VKD3D_SM5_TESSELLATOR_SHIFT;
- priv->p.program->tess_partitioning = ins->declaration.tessellator_partitioning;
+ priv->program->tess_partitioning = ins->declaration.tessellator_partitioning;
}
static void shader_sm5_read_dcl_tessellator_output_primitive(struct vkd3d_shader_instruction *ins, uint32_t opcode,
@@ -1288,7 +1290,7 @@ static void shader_sm5_read_dcl_tessellator_output_primitive(struct vkd3d_shader
{
ins->declaration.tessellator_output_primitive = (opcode_token & VKD3D_SM5_TESSELLATOR_MASK)
>> VKD3D_SM5_TESSELLATOR_SHIFT;
- priv->p.program->tess_output_primitive = ins->declaration.tessellator_output_primitive;
+ priv->program->tess_output_primitive = ins->declaration.tessellator_output_primitive;
}
static void shader_sm5_read_dcl_hs_max_tessfactor(struct vkd3d_shader_instruction *ins, uint32_t opcode,
@@ -1300,7 +1302,7 @@ static void shader_sm5_read_dcl_hs_max_tessfactor(struct vkd3d_shader_instructio
static void shader_sm5_read_dcl_thread_group(struct vkd3d_shader_instruction *ins, uint32_t opcode,
uint32_t opcode_token, const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *sm4)
{
- struct vsir_program *program = sm4->p.program;
+ struct vsir_program *program = sm4->program;
ins->declaration.thread_group_size.x = *tokens++;
ins->declaration.thread_group_size.y = *tokens++;
@@ -2009,7 +2011,7 @@ static bool shader_sm4_read_reg_idx(struct vkd3d_shader_sm4_parser *priv, const
{
if (addressing & VKD3D_SM4_ADDRESSING_RELATIVE)
{
- struct vkd3d_shader_src_param *rel_addr = vsir_program_get_src_params(priv->p.program, 1);
+ struct vkd3d_shader_src_param *rel_addr = vsir_program_get_src_params(priv->program, 1);
if (!(reg_idx->rel_addr = rel_addr))
{
@@ -2284,7 +2286,7 @@ static bool register_is_control_point_input(const struct vkd3d_shader_register *
{
return reg->type == VKD3DSPR_INCONTROLPOINT || reg->type == VKD3DSPR_OUTCONTROLPOINT
|| (reg->type == VKD3DSPR_INPUT && (priv->phase == VSIR_OP_HS_CONTROL_POINT_PHASE
- || priv->p.program->shader_version.type == VKD3D_SHADER_TYPE_GEOMETRY));
+ || priv->program->shader_version.type == VKD3D_SHADER_TYPE_GEOMETRY));
}
static uint32_t mask_from_swizzle(uint32_t swizzle)
@@ -2608,8 +2610,8 @@ static void shader_sm4_read_instruction_modifier(uint32_t modifier, struct vkd3d
static void shader_sm4_read_instruction(struct vkd3d_shader_sm4_parser *sm4, struct vkd3d_shader_instruction *ins)
{
const struct vkd3d_sm4_opcode_info *opcode_info;
- struct vsir_program *program = sm4->p.program;
uint32_t opcode_token, opcode, previous_token;
+ struct vsir_program *program = sm4->program;
struct vkd3d_shader_dst_param *dst_params;
struct vkd3d_shader_src_param *src_params;
const uint32_t **ptr = &sm4->ptr;
@@ -2814,8 +2816,9 @@ static bool shader_sm4_init(struct vkd3d_shader_sm4_parser *sm4, struct vsir_pro
if (!vsir_program_init(program, compile_info,
&version, token_count / 7u + 20, VSIR_CF_STRUCTURED, VSIR_NORMALISED_SM4))
return false;
- vkd3d_shader_parser_init(&sm4->p, program, message_context, compile_info->source_name);
+ vkd3d_shader_parser_init(&sm4->p, message_context, compile_info->source_name);
sm4->ptr = sm4->start;
+ sm4->program = program;
init_sm4_lookup_tables(&sm4->lookup);
@@ -3692,7 +3695,7 @@ static void write_sm4_instruction(const struct tpf_compiler *tpf, const struct s
static void tpf_dcl_constant_buffer(const struct tpf_compiler *tpf, const struct vkd3d_shader_instruction *ins)
{
const struct vkd3d_shader_constant_buffer *cb = &ins->declaration.cb;
- size_t size = (cb->size + 3) / 4;
+ size_t size = cb->size / VKD3D_VEC4_SIZE / sizeof(float);
struct sm4_instruction instr =
{
@@ -4222,6 +4225,7 @@ static void tpf_handle_instruction(struct tpf_compiler *tpf, const struct vkd3d_
case VSIR_OP_DCL:
case VSIR_OP_DCL_RESOURCE_RAW:
+ case VSIR_OP_DCL_RESOURCE_STRUCTURED:
case VSIR_OP_DCL_UAV_RAW:
case VSIR_OP_DCL_UAV_STRUCTURED:
case VSIR_OP_DCL_UAV_TYPED:
@@ -4305,6 +4309,7 @@ static void tpf_handle_instruction(struct tpf_compiler *tpf, const struct vkd3d_
case VSIR_OP_LD:
case VSIR_OP_LD2DMS:
case VSIR_OP_LD_RAW:
+ case VSIR_OP_LD_STRUCTURED:
case VSIR_OP_LD_UAV_TYPED:
case VSIR_OP_LOG:
case VSIR_OP_LOOP:
diff --git a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c
index 5fcc836aae1..6949c1cd38f 100644
--- a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c
+++ b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c
@@ -23,6 +23,8 @@
#include <stdio.h>
#include <math.h>
+/* VKD3D_DEBUG_ENV_NAME("VKD3D_SHADER_DEBUG"); */
+
static inline int char_to_int(char c)
{
if ('0' <= c && c <= '9')
@@ -722,14 +724,13 @@ uint64_t vkd3d_shader_init_config_flags(void)
return config_flags;
}
-void vkd3d_shader_parser_init(struct vkd3d_shader_parser *parser, struct vsir_program *program,
+void vkd3d_shader_parser_init(struct vkd3d_shader_parser *parser,
struct vkd3d_shader_message_context *message_context, const char *source_name)
{
parser->message_context = message_context;
parser->location.source_name = source_name;
parser->location.line = 1;
parser->location.column = 0;
- parser->program = program;
}
void VKD3D_PRINTF_FUNC(3, 4) vkd3d_shader_parser_error(struct vkd3d_shader_parser *parser,
@@ -1683,6 +1684,7 @@ static int vsir_program_scan(struct vsir_program *program, const struct vkd3d_sh
struct vsir_program_iterator it = vsir_program_iterator(&program->instructions);
struct vkd3d_shader_scan_combined_resource_sampler_info *combined_sampler_info;
struct vkd3d_shader_scan_hull_shader_tessellation_info *tessellation_info;
+ struct vkd3d_shader_scan_thread_group_size_info *thread_group_size_info;
struct vkd3d_shader_scan_descriptor_info *descriptor_info;
struct vkd3d_shader_scan_signature_info *signature_info;
struct vkd3d_shader_scan_context context;
@@ -1704,6 +1706,7 @@ static int vsir_program_scan(struct vsir_program *program, const struct vkd3d_sh
}
tessellation_info = vkd3d_find_struct(compile_info->next, SCAN_HULL_SHADER_TESSELLATION_INFO);
+ thread_group_size_info = vkd3d_find_struct(compile_info->next, SCAN_THREAD_GROUP_SIZE_INFO);
vkd3d_shader_scan_context_init(&context, &program->shader_version, compile_info,
add_descriptor_info ? &program->descriptors : NULL, combined_sampler_info, message_context);
@@ -1756,6 +1759,13 @@ static int vsir_program_scan(struct vsir_program *program, const struct vkd3d_sh
tessellation_info->partitioning = context.partitioning;
}
+ if (!ret && thread_group_size_info)
+ {
+ thread_group_size_info->x = program->thread_group_size.x;
+ thread_group_size_info->y = program->thread_group_size.y;
+ thread_group_size_info->z = program->thread_group_size.z;
+ }
+
if (ret < 0)
{
if (combined_sampler_info)
@@ -2182,6 +2192,9 @@ const enum vkd3d_shader_target_type *vkd3d_shader_get_supported_target_types(
VKD3D_SHADER_TARGET_D3D_BYTECODE,
VKD3D_SHADER_TARGET_DXBC_TPF,
VKD3D_SHADER_TARGET_FX,
+#ifdef VKD3D_SHADER_UNSUPPORTED_MSL
+ VKD3D_SHADER_TARGET_MSL,
+#endif
};
static const enum vkd3d_shader_target_type d3dbc_types[] =
@@ -2253,6 +2266,7 @@ int vkd3d_shader_preprocess(const struct vkd3d_shader_compile_info *compile_info
struct vkd3d_shader_code *out, char **messages)
{
struct vkd3d_shader_message_context message_context;
+ struct shader_dump_data dump_data;
int ret;
TRACE("compile_info %p, out %p, messages %p.\n", compile_info, out, messages);
@@ -2265,7 +2279,11 @@ int vkd3d_shader_preprocess(const struct vkd3d_shader_compile_info *compile_info
vkd3d_shader_message_context_init(&message_context, compile_info->log_level);
- ret = preproc_lexer_parse(compile_info, out, &message_context);
+ fill_shader_dump_data(compile_info, &dump_data);
+ vkd3d_shader_dump_shader(&dump_data, compile_info->source.code, compile_info->source.size, SHADER_DUMP_TYPE_SOURCE);
+
+ if ((ret = preproc_lexer_parse(compile_info, out, &message_context)) >= 0)
+ vkd3d_shader_dump_shader(&dump_data, out->code, out->size, SHADER_DUMP_TYPE_PREPROC);
vkd3d_shader_message_context_trace_messages(&message_context);
if (!vkd3d_shader_message_context_copy_messages(&message_context, messages))
@@ -2279,204 +2297,6 @@ void vkd3d_shader_set_log_callback(PFN_vkd3d_log callback)
vkd3d_dbg_set_log_callback(callback);
}
-static struct vkd3d_shader_param_node *shader_param_allocator_node_create(
- struct vkd3d_shader_param_allocator *allocator)
-{
- struct vkd3d_shader_param_node *node;
-
- if (!(node = vkd3d_malloc(offsetof(struct vkd3d_shader_param_node, param[allocator->count * allocator->stride]))))
- return NULL;
- node->next = NULL;
- return node;
-}
-
-static void shader_param_allocator_init(struct vkd3d_shader_param_allocator *allocator,
- size_t count, size_t stride)
-{
- allocator->count = max(count, MAX_REG_OUTPUT);
- allocator->stride = stride;
- allocator->head = NULL;
- allocator->current = NULL;
- allocator->index = allocator->count;
-}
-
-static void shader_param_allocator_destroy(struct vkd3d_shader_param_allocator *allocator)
-{
- struct vkd3d_shader_param_node *current = allocator->head;
-
- while (current)
- {
- struct vkd3d_shader_param_node *next = current->next;
- vkd3d_free(current);
- current = next;
- }
-}
-
-void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, size_t count)
-{
- void *params;
-
- if (!allocator->current || count > allocator->count - allocator->index)
- {
- struct vkd3d_shader_param_node *next;
-
- /* Monolithic switch has no definite parameter count limit. */
- allocator->count = max(allocator->count, count);
-
- if (!(next = shader_param_allocator_node_create(allocator)))
- return NULL;
- if (allocator->current)
- allocator->current->next = next;
- else
- allocator->head = next;
- allocator->current = next;
- allocator->index = 0;
- }
-
- params = &allocator->current->param[allocator->index * allocator->stride];
- allocator->index += count;
- return params;
-}
-
-bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instructions, size_t reserve)
-{
- memset(instructions, 0, sizeof(*instructions));
- /* Size the parameter initial allocations so they are large enough for most shaders. The
- * code path for chained allocations will be tested if a few shaders need to use it. */
- shader_param_allocator_init(&instructions->dst_params, reserve - reserve / 8u,
- sizeof(struct vkd3d_shader_dst_param));
- shader_param_allocator_init(&instructions->src_params, reserve * 2u, sizeof(struct vkd3d_shader_src_param));
- return shader_instruction_array_reserve(instructions, reserve);
-}
-
-bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, size_t reserve)
-{
- if (!vkd3d_array_reserve((void **)&instructions->elements, &instructions->capacity, reserve,
- sizeof(*instructions->elements)))
- {
- ERR("Failed to allocate instructions.\n");
- return false;
- }
- return true;
-}
-
-bool shader_instruction_array_insert_at(struct vkd3d_shader_instruction_array *instructions,
- size_t idx, size_t count)
-{
- VKD3D_ASSERT(idx <= instructions->count);
-
- if (!shader_instruction_array_reserve(instructions, instructions->count + count))
- return false;
-
- memmove(&instructions->elements[idx + count], &instructions->elements[idx],
- (instructions->count - idx) * sizeof(*instructions->elements));
- memset(&instructions->elements[idx], 0, count * sizeof(*instructions->elements));
-
- instructions->count += count;
-
- return true;
-}
-
-bool shader_instruction_array_add_icb(struct vkd3d_shader_instruction_array *instructions,
- struct vkd3d_shader_immediate_constant_buffer *icb)
-{
- if (!vkd3d_array_reserve((void **)&instructions->icbs, &instructions->icb_capacity, instructions->icb_count + 1,
- sizeof(*instructions->icbs)))
- return false;
- instructions->icbs[instructions->icb_count++] = icb;
- return true;
-}
-
-static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
- struct vkd3d_shader_instruction_array *instructions, const struct vkd3d_shader_src_param *params,
- size_t count);
-
-static bool shader_register_clone_relative_addresses(struct vkd3d_shader_register *reg,
- struct vkd3d_shader_instruction_array *instructions)
-{
- unsigned int i;
-
- for (i = 0; i < reg->idx_count; ++i)
- {
- if (!reg->idx[i].rel_addr)
- continue;
-
- if (!(reg->idx[i].rel_addr = shader_instruction_array_clone_src_params(instructions, reg->idx[i].rel_addr, 1)))
- return false;
- }
-
- return true;
-}
-
-static struct vkd3d_shader_dst_param *shader_instruction_array_clone_dst_params(
- struct vkd3d_shader_instruction_array *instructions, const struct vkd3d_shader_dst_param *params,
- size_t count)
-{
- struct vkd3d_shader_dst_param *dst_params;
- size_t i;
-
- if (!(dst_params = shader_dst_param_allocator_get(&instructions->dst_params, count)))
- return NULL;
-
- memcpy(dst_params, params, count * sizeof(*params));
- for (i = 0; i < count; ++i)
- {
- if (!shader_register_clone_relative_addresses(&dst_params[i].reg, instructions))
- return NULL;
- }
-
- return dst_params;
-}
-
-static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params(
- struct vkd3d_shader_instruction_array *instructions, const struct vkd3d_shader_src_param *params,
- size_t count)
-{
- struct vkd3d_shader_src_param *src_params;
- size_t i;
-
- if (!(src_params = shader_src_param_allocator_get(&instructions->src_params, count)))
- return NULL;
-
- memcpy(src_params, params, count * sizeof(*params));
- for (i = 0; i < count; ++i)
- {
- if (!shader_register_clone_relative_addresses(&src_params[i].reg, instructions))
- return NULL;
- }
-
- return src_params;
-}
-
-/* NOTE: Immediate constant buffers are not cloned, so the source must not be destroyed while the
- * destination is in use. This seems like a reasonable requirement given how this is currently used. */
-bool shader_instruction_array_clone_instruction(struct vkd3d_shader_instruction_array *instructions,
- size_t dst, size_t src)
-{
- struct vkd3d_shader_instruction *ins = &instructions->elements[dst];
-
- *ins = instructions->elements[src];
-
- if (ins->dst_count && ins->dst && !(ins->dst = shader_instruction_array_clone_dst_params(instructions,
- ins->dst, ins->dst_count)))
- return false;
-
- return !ins->src_count || !!(ins->src = shader_instruction_array_clone_src_params(instructions,
- ins->src, ins->src_count));
-}
-
-void shader_instruction_array_destroy(struct vkd3d_shader_instruction_array *instructions)
-{
- unsigned int i;
-
- vkd3d_free(instructions->elements);
- shader_param_allocator_destroy(&instructions->dst_params);
- shader_param_allocator_destroy(&instructions->src_params);
- for (i = 0; i < instructions->icb_count; ++i)
- vkd3d_free(instructions->icbs[i]);
- vkd3d_free(instructions->icbs);
-}
-
void vkd3d_shader_build_varying_map(const struct vkd3d_shader_signature *output_signature,
const struct vkd3d_shader_signature *input_signature,
unsigned int *ret_count, struct vkd3d_shader_varying_map *varyings)
diff --git a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h
index e758c16b3d4..c00a7825610 100644
--- a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h
+++ b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h
@@ -213,7 +213,7 @@ enum vkd3d_shader_error
VKD3D_SHADER_ERROR_DXIL_INVALID_OPERAND_COUNT = 8005,
VKD3D_SHADER_ERROR_DXIL_INVALID_TYPE_TABLE = 8006,
VKD3D_SHADER_ERROR_DXIL_INVALID_VALUE_SYMTAB = 8007,
- VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED_BITCODE_FORMAT = 8008,
+ VKD3D_SHADER_ERROR_DXIL_UNSUPPORTED = 8008,
VKD3D_SHADER_ERROR_DXIL_INVALID_FUNCTION_DCL = 8009,
VKD3D_SHADER_ERROR_DXIL_INVALID_TYPE_ID = 8010,
VKD3D_SHADER_ERROR_DXIL_INVALID_MODULE = 8011,
@@ -716,7 +716,9 @@ enum vsir_data_type
VSIR_DATA_F32,
VSIR_DATA_F64,
+ VSIR_DATA_I16,
VSIR_DATA_I32,
+ VSIR_DATA_I64,
VSIR_DATA_U8,
VSIR_DATA_U16,
@@ -734,10 +736,13 @@ enum vsir_data_type
VSIR_DATA_TYPE_COUNT,
};
+const char *vsir_data_type_get_name(enum vsir_data_type t, const char *error);
+
static inline bool data_type_is_integer(enum vsir_data_type data_type)
{
- return data_type == VSIR_DATA_I32 || data_type == VSIR_DATA_U8 || data_type == VSIR_DATA_U16
- || data_type == VSIR_DATA_U32 || data_type == VSIR_DATA_U64;
+ return data_type == VSIR_DATA_I16 || data_type == VSIR_DATA_I32 || data_type == VSIR_DATA_I64
+ || data_type == VSIR_DATA_U8 || data_type == VSIR_DATA_U16 || data_type == VSIR_DATA_U32
+ || data_type == VSIR_DATA_U64;
}
static inline bool data_type_is_bool(enum vsir_data_type data_type)
@@ -752,7 +757,7 @@ static inline bool data_type_is_floating_point(enum vsir_data_type data_type)
static inline bool data_type_is_64_bit(enum vsir_data_type data_type)
{
- return data_type == VSIR_DATA_F64 || data_type == VSIR_DATA_U64;
+ return data_type == VSIR_DATA_F64 || data_type == VSIR_DATA_I64 || data_type == VSIR_DATA_U64;
}
enum vsir_dimension
@@ -1439,15 +1444,11 @@ struct vkd3d_shader_instruction_array
struct vkd3d_shader_src_param *outpointid_param;
};
-bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instructions, size_t reserve);
bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, size_t reserve);
bool shader_instruction_array_insert_at(struct vkd3d_shader_instruction_array *instructions,
size_t idx, size_t count);
bool shader_instruction_array_add_icb(struct vkd3d_shader_instruction_array *instructions,
struct vkd3d_shader_immediate_constant_buffer *icb);
-bool shader_instruction_array_clone_instruction(struct vkd3d_shader_instruction_array *instructions,
- size_t dst, size_t src);
-void shader_instruction_array_destroy(struct vkd3d_shader_instruction_array *instructions);
struct vsir_program_iterator
{
@@ -1510,6 +1511,38 @@ static inline bool vsir_program_iterator_insert_after(struct vsir_program_iterat
return shader_instruction_array_insert_at(it->array, it->idx + 1, count);
}
+/* When insertion takes place, argument `it' is updated to point to the same
+ * instruction as before the insertion, and the optional argument `ins_it' is
+ * initialized to point to the first inserted instruction.
+ * A pointer to the first inserted instruction is returned. */
+static inline struct vkd3d_shader_instruction *vsir_program_iterator_insert_before(
+ struct vsir_program_iterator *it, struct vsir_program_iterator *ins_it, size_t count)
+{
+ VKD3D_ASSERT(it != ins_it);
+ VKD3D_ASSERT(it->idx != SIZE_MAX);
+
+ if (!shader_instruction_array_insert_at(it->array, it->idx, count))
+ return NULL;
+
+ *ins_it = *it;
+ it->idx += count;
+
+ return vsir_program_iterator_current(ins_it);
+}
+
+/* When insertion takes place, argument `it' is updated to point to the first
+ * inserted instruction. A pointer to this first inserted instruction is
+ * returned. */
+static inline struct vkd3d_shader_instruction *vsir_program_iterator_insert_before_and_move(
+ struct vsir_program_iterator *it, size_t count)
+{
+ VKD3D_ASSERT(it->idx != SIZE_MAX);
+
+ if (!shader_instruction_array_insert_at(it->array, it->idx, count))
+ return NULL;
+ return vsir_program_iterator_current(it);
+}
+
enum vkd3d_shader_config_flags
{
VKD3D_SHADER_CONFIG_FLAG_FORCE_VALIDATION = 0x00000001,
@@ -1651,13 +1684,12 @@ struct vkd3d_shader_parser
{
struct vkd3d_shader_message_context *message_context;
struct vkd3d_shader_location location;
- struct vsir_program *program;
bool failed;
};
void vkd3d_shader_parser_error(struct vkd3d_shader_parser *parser,
enum vkd3d_shader_error error, const char *format, ...) VKD3D_PRINTF_FUNC(3, 4);
-void vkd3d_shader_parser_init(struct vkd3d_shader_parser *parser, struct vsir_program *program,
+void vkd3d_shader_parser_init(struct vkd3d_shader_parser *parser,
struct vkd3d_shader_message_context *message_context, const char *source_name);
void vkd3d_shader_parser_warning(struct vkd3d_shader_parser *parser,
enum vkd3d_shader_error error, const char *format, ...) VKD3D_PRINTF_FUNC(3, 4);
@@ -1852,20 +1884,28 @@ static inline enum vkd3d_shader_component_type vkd3d_component_type_from_data_ty
{
case VSIR_DATA_BOOL:
return VKD3D_SHADER_COMPONENT_BOOL;
- case VSIR_DATA_F16: /* Minimum precision. TODO: native 16-bit */
+ case VSIR_DATA_F16:
+ return VKD3D_SHADER_COMPONENT_FLOAT16;
case VSIR_DATA_F32:
case VSIR_DATA_SNORM:
case VSIR_DATA_UNORM:
return VKD3D_SHADER_COMPONENT_FLOAT;
case VSIR_DATA_F64:
return VKD3D_SHADER_COMPONENT_DOUBLE;
+ case VSIR_DATA_I16:
+ return VKD3D_SHADER_COMPONENT_INT16;
case VSIR_DATA_I32:
return VKD3D_SHADER_COMPONENT_INT;
- case VSIR_DATA_U16: /* Minimum precision. TODO: native 16-bit */
+ case VSIR_DATA_I64:
+ return VKD3D_SHADER_COMPONENT_INT64;
+ case VSIR_DATA_U16:
+ return VKD3D_SHADER_COMPONENT_UINT16;
case VSIR_DATA_U32:
return VKD3D_SHADER_COMPONENT_UINT;
case VSIR_DATA_U64:
return VKD3D_SHADER_COMPONENT_UINT64;
+ case VSIR_DATA_UNUSED:
+ return VKD3D_SHADER_COMPONENT_VOID;
default:
FIXME("Unhandled data type %#x.\n", data_type);
/* fall-through */
@@ -1878,23 +1918,41 @@ static inline enum vsir_data_type vsir_data_type_from_component_type(enum vkd3d_
{
switch (component_type)
{
- case VKD3D_SHADER_COMPONENT_FLOAT:
- return VSIR_DATA_F32;
+ case VKD3D_SHADER_COMPONENT_VOID:
+ return VSIR_DATA_UNUSED;
case VKD3D_SHADER_COMPONENT_UINT:
return VSIR_DATA_U32;
case VKD3D_SHADER_COMPONENT_INT:
return VSIR_DATA_I32;
+ case VKD3D_SHADER_COMPONENT_FLOAT:
+ return VSIR_DATA_F32;
+ case VKD3D_SHADER_COMPONENT_BOOL:
+ return VSIR_DATA_BOOL;
case VKD3D_SHADER_COMPONENT_DOUBLE:
return VSIR_DATA_F64;
- default:
- FIXME("Unhandled component type %#x.\n", component_type);
- return VSIR_DATA_F32;
+ case VKD3D_SHADER_COMPONENT_UINT64:
+ return VSIR_DATA_U64;
+ case VKD3D_SHADER_COMPONENT_INT64:
+ return VSIR_DATA_I64;
+ case VKD3D_SHADER_COMPONENT_FLOAT16:
+ return VSIR_DATA_F16;
+ case VKD3D_SHADER_COMPONENT_UINT16:
+ return VSIR_DATA_U16;
+ case VKD3D_SHADER_COMPONENT_INT16:
+ return VSIR_DATA_I16;
+ case VKD3D_SHADER_COMPONENT_TYPE_FORCE_32BIT:
+ break;
}
+
+ FIXME("Unhandled component type %#x.\n", component_type);
+
+ return VSIR_DATA_UNUSED;
}
static inline bool component_type_is_64_bit(enum vkd3d_shader_component_type component_type)
{
- return component_type == VKD3D_SHADER_COMPONENT_DOUBLE || component_type == VKD3D_SHADER_COMPONENT_UINT64;
+ return component_type == VKD3D_SHADER_COMPONENT_DOUBLE || component_type == VKD3D_SHADER_COMPONENT_INT64
+ || component_type == VKD3D_SHADER_COMPONENT_UINT64;
}
static inline unsigned int vsir_write_mask_get_component_idx(uint32_t write_mask)
diff --git a/libs/vkd3d/libs/vkd3d-utils/vkd3d_utils_main.c b/libs/vkd3d/libs/vkd3d-utils/vkd3d_utils_main.c
index f2967835b62..fea8c2440d1 100644
--- a/libs/vkd3d/libs/vkd3d-utils/vkd3d_utils_main.c
+++ b/libs/vkd3d/libs/vkd3d-utils/vkd3d_utils_main.c
@@ -19,6 +19,8 @@
#include "vkd3d_utils_private.h"
#undef D3D12CreateDevice
+/* VKD3D_DEBUG_ENV_NAME("VKD3D_DEBUG"); */
+
static const char *debug_d3d_blob_part(D3D_BLOB_PART part)
{
switch (part)
@@ -269,7 +271,7 @@ HRESULT WINAPI D3DCompile2VKD3D(const void *data, SIZE_T data_size, const char *
option = &options[0];
option->name = VKD3D_SHADER_COMPILE_OPTION_API_VERSION;
- option->value = VKD3D_SHADER_API_VERSION_1_17;
+ option->value = VKD3D_SHADER_API_VERSION_CURRENT;
compile_info.type = VKD3D_SHADER_STRUCTURE_TYPE_COMPILE_INFO;
compile_info.next = &preprocess_info;
@@ -433,7 +435,7 @@ HRESULT WINAPI D3DPreprocess(const void *data, SIZE_T size, const char *filename
static const struct vkd3d_shader_compile_option options[] =
{
- {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_1_17},
+ {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_CURRENT},
};
TRACE("data %p, size %"PRIuPTR", filename %s, macros %p, include %p, preprocessed_blob %p, messages_blob %p.\n",
@@ -482,7 +484,10 @@ HRESULT WINAPI D3DPreprocess(const void *data, SIZE_T size, const char *filename
if (!ret)
{
- if (FAILED(hr = vkd3d_blob_create((void *)preprocessed_code.code, preprocessed_code.size, preprocessed_blob)))
+ /* vkd3d-shader output is null-terminated, but the null terminator isn't
+ * included in the size. Increase the size to account for that. */
+ if (FAILED(hr = vkd3d_blob_create((void *)preprocessed_code.code,
+ preprocessed_code.size + 1, preprocessed_blob)))
{
vkd3d_shader_free_shader_code(&preprocessed_code);
return hr;
@@ -979,7 +984,7 @@ HRESULT WINAPI D3DDisassemble(const void *data, SIZE_T data_size,
static const struct vkd3d_shader_compile_option options[] =
{
- {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_1_17},
+ {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_CURRENT},
};
TRACE("data %p, data_size %"PRIuPTR", flags %#x, comments %p, blob %p.\n",
@@ -1032,7 +1037,9 @@ HRESULT WINAPI D3DDisassemble(const void *data, SIZE_T data_size,
return hresult_from_vkd3d_result(ret);
}
- if (FAILED(hr = vkd3d_blob_create((void *)output.code, output.size, blob)))
+ /* vkd3d-shader output is null-terminated, but the null terminator isn't
+ * included in the size. Increase the size to account for that. */
+ if (FAILED(hr = vkd3d_blob_create((void *)output.code, output.size + 1, blob)))
vkd3d_shader_free_shader_code(&output);
return hr;
diff --git a/libs/vkd3d/libs/vkd3d/command.c b/libs/vkd3d/libs/vkd3d/command.c
index 074d8430585..d933e7ec463 100644
--- a/libs/vkd3d/libs/vkd3d/command.c
+++ b/libs/vkd3d/libs/vkd3d/command.c
@@ -3049,7 +3049,7 @@ static void d3d12_command_list_update_descriptor_table(struct d3d12_command_list
if (descriptor_count > range->vk_binding_count)
{
- ERR("Heap descriptor count %u exceeds maximum Vulkan count %u. Reducing to the Vulkan maximum.\n",
+ MESSAGE("Heap descriptor count %u exceeds maximum Vulkan count %u. Reducing to the Vulkan maximum.\n",
descriptor_count, range->vk_binding_count);
descriptor_count = range->vk_binding_count;
}
diff --git a/libs/vkd3d/libs/vkd3d/state.c b/libs/vkd3d/libs/vkd3d/state.c
index 6bbd6533b74..b6055a50a99 100644
--- a/libs/vkd3d/libs/vkd3d/state.c
+++ b/libs/vkd3d/libs/vkd3d/state.c
@@ -2391,7 +2391,7 @@ static HRESULT create_shader_stage(struct d3d12_device *device,
const struct vkd3d_shader_compile_option options[] =
{
- {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_1_17},
+ {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_CURRENT},
{VKD3D_SHADER_COMPILE_OPTION_TYPED_UAV, typed_uav_compile_option(device)},
{VKD3D_SHADER_COMPILE_OPTION_WRITE_TESS_GEOM_POINT_SIZE, 0},
{VKD3D_SHADER_COMPILE_OPTION_FEATURE, feature_flags_compile_option(device)},
@@ -2456,7 +2456,7 @@ static int vkd3d_scan_dxbc(const struct d3d12_device *device, const D3D12_SHADER
const struct vkd3d_shader_compile_option options[] =
{
- {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_1_17},
+ {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_CURRENT},
{VKD3D_SHADER_COMPILE_OPTION_TYPED_UAV, typed_uav_compile_option(device)},
};
@@ -4135,7 +4135,7 @@ static int compile_hlsl_cs(const struct vkd3d_shader_code *hlsl, struct vkd3d_sh
static const struct vkd3d_shader_compile_option options[] =
{
- {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_1_17},
+ {VKD3D_SHADER_COMPILE_OPTION_API_VERSION, VKD3D_SHADER_API_VERSION_CURRENT},
};
info.type = VKD3D_SHADER_STRUCTURE_TYPE_COMPILE_INFO;
diff --git a/libs/vkd3d/libs/vkd3d/utils.c b/libs/vkd3d/libs/vkd3d/utils.c
index c2832a61f67..2d0510e5456 100644
--- a/libs/vkd3d/libs/vkd3d/utils.c
+++ b/libs/vkd3d/libs/vkd3d/utils.c
@@ -703,7 +703,7 @@ const char *debug_vk_extent_3d(VkExtent3D extent)
const char *debug_vk_queue_flags(VkQueueFlags flags)
{
- char buffer[191];
+ char buffer[222];
buffer[0] = '\0';
#define FLAG_TO_STR(f) if (flags & f) { strcat(buffer, " | "#f); flags &= ~f; }
@@ -716,6 +716,7 @@ const char *debug_vk_queue_flags(VkQueueFlags flags)
#define FLAG_TO_STR(f, n) if (flags & f) { strcat(buffer, " | "#n); flags &= ~f; }
FLAG_TO_STR(0x20, VK_QUEUE_VIDEO_DECODE_BIT_KHR)
FLAG_TO_STR(0x40, VK_QUEUE_VIDEO_ENCODE_BIT_KHR)
+ FLAG_TO_STR(0x100, VK_QUEUE_OPTICAL_FLOW_BIT_NV)
#undef FLAG_TO_STR
if (flags)
FIXME("Unrecognized flag(s) %#x.\n", flags);
--
2.51.0