2
0
Эх сурвалжийг харах

Fixed debug info alignment in min16 types. (#3257)

Adam Yang 4 жил өмнө
parent
commit
ee3303f61d

+ 3 - 2
lib/Transforms/Scalar/DxilEliminateVector.cpp

@@ -134,8 +134,9 @@ bool DxilEliminateVector::TryRewriteDebugInfoForVector(InsertElementInst *IE) {
       if (!Elements[i])
       if (!Elements[i])
         continue;
         continue;
 
 
-      unsigned ElementSize = DL.getTypeAllocSizeInBits(Elements[i]->getType());
-      DIExpression *Expr = DIB.createBitPieceExpression(BitpieceOffset + i * ElementSize, ElementSize);
+      unsigned ElementSize = DL.getTypeSizeInBits(Elements[i]->getType());
+      unsigned ElementAlign = DL.getTypeAllocSizeInBits(Elements[i]->getType());
+      DIExpression *Expr = DIB.createBitPieceExpression(BitpieceOffset + i * ElementAlign, ElementSize);
       DIB.insertDbgValueIntrinsic(Elements[i], 0, DVI->getVariable(), Expr, DVI->getDebugLoc(), DVI);
       DIB.insertDbgValueIntrinsic(Elements[i], 0, DVI->getVariable(), Expr, DVI->getDebugLoc(), DVI);
 
 
       Changed = true;
       Changed = true;

+ 1 - 1
lib/Transforms/Scalar/ScalarReplAggregatesHLSL.cpp

@@ -233,7 +233,7 @@ static void addDebugInfoForElements(Value *ParentVal,
     // The bit_piece can only represent the leading contiguous bytes.
     // The bit_piece can only represent the leading contiguous bytes.
     // If strides are involved, we'll need additional metadata.
     // If strides are involved, we'll need additional metadata.
     Type *ElemTy = Elems[ElemIdx]->getType()->getPointerElementType();
     Type *ElemTy = Elems[ElemIdx]->getType()->getPointerElementType();
-    unsigned ElemBitPieceSize = (unsigned)DatLayout.getTypeAllocSizeInBits(ElemTy);
+    unsigned ElemBitPieceSize = (unsigned)DatLayout.getTypeStoreSizeInBits(ElemTy);
     for (const DxilDIArrayDim& ArrayDim : DIArrayDims)
     for (const DxilDIArrayDim& ArrayDim : DIArrayDims)
       ElemBitPieceSize /= ArrayDim.NumElements;
       ElemBitPieceSize /= ArrayDim.NumElements;
 
 

+ 11 - 3
tools/clang/lib/AST/ASTContext.cpp

@@ -39,6 +39,7 @@
 #include "llvm/Support/Capacity.h"
 #include "llvm/Support/Capacity.h"
 #include "llvm/Support/MathExtras.h"
 #include "llvm/Support/MathExtras.h"
 #include "llvm/Support/raw_ostream.h"
 #include "llvm/Support/raw_ostream.h"
+#include "llvm/Support/MathExtras.h" // HLSL Change
 #include <map>
 #include <map>
 
 
 using namespace clang;
 using namespace clang;
@@ -1575,6 +1576,7 @@ TypeInfo ASTContext::getTypeInfoImpl(const Type *T) const {
     // HLSL Change Begins.
     // HLSL Change Begins.
     // Vector align to its element.
     // Vector align to its element.
     if (getLangOpts().HLSL) {
     if (getLangOpts().HLSL) {
+      Width = llvm::RoundUpToAlignment(EltInfo.Width, EltInfo.Align) * VT->getNumElements(); // Match data layout's behaviour
       Align = EltInfo.Align;
       Align = EltInfo.Align;
     }
     }
     // HLSL Change Ends.
     // HLSL Change Ends.
@@ -1624,7 +1626,6 @@ TypeInfo ASTContext::getTypeInfoImpl(const Type *T) const {
       Width = Target->getChar32Width();
       Width = Target->getChar32Width();
       Align = Target->getChar32Align();
       Align = Target->getChar32Align();
       break;
       break;
-    case BuiltinType::Min16UInt: // HLSL Change
     case BuiltinType::UShort:
     case BuiltinType::UShort:
     case BuiltinType::Short:
     case BuiltinType::Short:
       Width = Target->getShortWidth();
       Width = Target->getShortWidth();
@@ -1667,12 +1668,19 @@ TypeInfo ASTContext::getTypeInfoImpl(const Type *T) const {
     case BuiltinType::Min10Float:
     case BuiltinType::Min10Float:
     case BuiltinType::Min16Float:
     case BuiltinType::Min16Float:
       Width = 16;
       Width = 16;
-      Align = 16;
+      if (!getLangOpts().UseMinPrecision)
+        Align = 16;
+      else
+        Align = 32;
       break;
       break;
     case BuiltinType::Min12Int:
     case BuiltinType::Min12Int:
     case BuiltinType::Min16Int:
     case BuiltinType::Min16Int:
+    case BuiltinType::Min16UInt:
       Width = 16;
       Width = 16;
-      Align = 16;
+      if (!getLangOpts().UseMinPrecision)
+        Align = 16;
+      else
+        Align = 32;
       break;
       break;
     // Treat literals as largest size possible here, as it will be used
     // Treat literals as largest size possible here, as it will be used
     // to determine MaxWidth in GetExprRange
     // to determine MaxWidth in GetExprRange

+ 37 - 0
tools/clang/test/HLSLFileCheck/dxil/debug/min16/min16float.hlsl

@@ -0,0 +1,37 @@
+// RUN: %dxc -E main -T cs_6_2 -Zi -Od %s | FileCheck %s
+// RUN: %dxc -E main -T cs_6_2 -Zi -Od %s -enable-16bit-types | FileCheck %s -check-prefix=CHECK16
+
+// CHECK-DAG: call void @llvm.dbg.value(metadata half 0xH3C00, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+// CHECK-DAG: call void @llvm.dbg.value(metadata half 0xH4000, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 32, 16)
+
+// CHECK16-DAG: call void @llvm.dbg.value(metadata half 0xH3C00, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+// CHECK16-DAG: call void @llvm.dbg.value(metadata half 0xH4000, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 16, 16)
+
+struct Foo
+{
+    min16float m_A;
+    min16float m_B;
+};
+RWTexture1D<float2> out_buf;
+
+[numthreads(1, 1, 1)]
+[RootSignature("")]
+[RootSignature("DescriptorTable(SRV(t0)), DescriptorTable(UAV(u0))")]
+void main()
+{
+    Foo foo = { 1, 2 };
+    min16float value1 = foo.m_B;
+    min16float value2 = foo.m_A;
+    out_buf[0] = float2(value1, value2);
+}
+
+// CHECK-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 64, align: 32, elements: ![[elements_md:[0-9]+]]
+// CHECK-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 16, align: 32
+// CHECK-DAG: !DIBasicType(name: "min16float", size: 16, align: 32, encoding: DW_ATE_float)
+
+// CHECK16-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 32, align: 16, elements: ![[elements_md:[0-9]+]]
+// CHECK16-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK16-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 16, align: 16
+// CHECK16-DAG: !DIBasicType(name: "min16float", size: 16, align: 16, encoding: DW_ATE_float)
+

+ 49 - 0
tools/clang/test/HLSLFileCheck/dxil/debug/min16/min16float_vec.hlsl

@@ -0,0 +1,49 @@
+// RUN: %dxc -E main -T cs_6_2 -Zi /Od %s | FileCheck %s
+// RUN: %dxc -E main -T cs_6_2 -Zi /Od %s -enable-16bit-types | FileCheck %s -check-prefix=CHECK16
+
+struct Foo
+{
+    min16float3 m_A;
+    min16float3 m_B;
+};
+
+StructuredBuffer<Foo> buf;
+RWTexture1D<float4> out_buf;
+
+[numthreads(1, 1, 1)]
+[RootSignature("DescriptorTable(SRV(t0)), DescriptorTable(UAV(u0))")]
+void main()
+{
+    Foo foo = buf[0];
+    // foo.m_B.x
+    // CHECK-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 96, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 48, 16)
+
+    // foo.m_B.y
+    // CHECK-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 128, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 64, 16)
+
+    // foo.m_B.z
+    // CHECK-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 160, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 80, 16)
+
+    // foo.m_A.x
+    // CHECK-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata half %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+
+    min16float value1 = foo.m_B.x;
+    min16float value2 = foo.m_B.y;
+    min16float value3 = foo.m_B.z;
+    min16float value4 = foo.m_A.x;
+    out_buf[0] = float4(value1, value2, value3, value4);
+}
+
+// CHECK-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 192, align: 32, elements: ![[elements_md:[0-9]+]]
+// CHECK-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 96, align: 32
+// CHECK-DAG: !DIBasicType(name: "min16float", size: 16, align: 32, encoding: DW_ATE_float)
+
+// CHECK16-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 96, align: 16, elements: ![[elements_md:[0-9]+]]
+// CHECK16-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK16-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 48, align: 16
+// CHECK16-DAG: !DIBasicType(name: "min16float", size: 16, align: 16, encoding: DW_ATE_float)

+ 37 - 0
tools/clang/test/HLSLFileCheck/dxil/debug/min16/min16int.hlsl

@@ -0,0 +1,37 @@
+// RUN: %dxc -E main -T cs_6_2 -Zi -Od %s | FileCheck %s
+// RUN: %dxc -E main -T cs_6_2 -Zi -Od %s -enable-16bit-types | FileCheck %s -check-prefix=CHECK16
+
+// CHECK-DAG: call void @llvm.dbg.value(metadata i16 1, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+// CHECK-DAG: call void @llvm.dbg.value(metadata i16 2, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 32, 16)
+
+// CHECK16-DAG: call void @llvm.dbg.value(metadata i16 1, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+// CHECK16-DAG: call void @llvm.dbg.value(metadata i16 2, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 16, 16)
+
+struct Foo
+{
+    min16int m_A;
+    min16int m_B;
+};
+RWTexture1D<int2> out_buf;
+
+[numthreads(1, 1, 1)]
+[RootSignature("")]
+[RootSignature("DescriptorTable(SRV(t0)), DescriptorTable(UAV(u0))")]
+void main()
+{
+    Foo foo = { 1, 2 };
+    min16int value1 = foo.m_B;
+    min16int value2 = foo.m_A;
+    out_buf[0] = int2(value1, value2);
+}
+
+// CHECK-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 64, align: 32, elements: ![[elements_md:[0-9]+]]
+// CHECK-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 16, align: 32
+// CHECK-DAG: !DIBasicType(name: "min16int", size: 16, align: 32, encoding: DW_ATE_signed)
+
+// CHECK16-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 32, align: 16, elements: ![[elements_md:[0-9]+]]
+// CHECK16-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK16-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 16, align: 16
+// CHECK16-DAG: !DIBasicType(name: "min16int", size: 16, align: 16, encoding: DW_ATE_signed)
+

+ 49 - 0
tools/clang/test/HLSLFileCheck/dxil/debug/min16/min16int_vec.hlsl

@@ -0,0 +1,49 @@
+// RUN: %dxc -E main -T cs_6_2 -Zi /Od %s | FileCheck %s
+// RUN: %dxc -E main -T cs_6_2 -Zi /Od %s -enable-16bit-types | FileCheck %s -check-prefix=CHECK16
+
+struct Foo
+{
+    min16int3 m_A;
+    min16int3 m_B;
+};
+
+StructuredBuffer<Foo> buf;
+RWTexture1D<int4> out_buf;
+
+[numthreads(1, 1, 1)]
+[RootSignature("DescriptorTable(SRV(t0)), DescriptorTable(UAV(u0))")]
+void main()
+{
+    Foo foo = buf[0];
+    // foo.m_B.x
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 96, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 48, 16)
+
+    // foo.m_B.y
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 128, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 64, 16)
+
+    // foo.m_B.z
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 160, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 80, 16)
+
+    // foo.m_A.x
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+
+    min16int value1 = foo.m_B.x;
+    min16int value2 = foo.m_B.y;
+    min16int value3 = foo.m_B.z;
+    min16int value4 = foo.m_A.x;
+    out_buf[0] = int4(value1, value2, value3, value4);
+}
+
+// CHECK-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 192, align: 32, elements: ![[elements_md:[0-9]+]]
+// CHECK-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 96, align: 32
+// CHECK-DAG: !DIBasicType(name: "min16int", size: 16, align: 32, encoding: DW_ATE_signed)
+
+// CHECK16-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 96, align: 16, elements: ![[elements_md:[0-9]+]]
+// CHECK16-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK16-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 48, align: 16
+// CHECK16-DAG: !DIBasicType(name: "min16int", size: 16, align: 16, encoding: DW_ATE_signed)

+ 37 - 0
tools/clang/test/HLSLFileCheck/dxil/debug/min16/min16uint.hlsl

@@ -0,0 +1,37 @@
+// RUN: %dxc -E main -T cs_6_2 -Zi -Od %s | FileCheck %s
+// RUN: %dxc -E main -T cs_6_2 -Zi -Od %s -enable-16bit-types | FileCheck %s -check-prefix=CHECK16
+
+// CHECK-DAG: call void @llvm.dbg.value(metadata i16 1, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+// CHECK-DAG: call void @llvm.dbg.value(metadata i16 2, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 32, 16)
+
+// CHECK16-DAG: call void @llvm.dbg.value(metadata i16 1, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+// CHECK16-DAG: call void @llvm.dbg.value(metadata i16 2, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 16, 16)
+
+struct Foo
+{
+    min16uint m_A;
+    min16uint m_B;
+};
+RWTexture1D<uint2> out_buf;
+
+[numthreads(1, 1, 1)]
+[RootSignature("")]
+[RootSignature("DescriptorTable(SRV(t0)), DescriptorTable(UAV(u0))")]
+void main()
+{
+    Foo foo = { 1, 2 };
+    min16uint value1 = foo.m_B;
+    min16uint value2 = foo.m_A;
+    out_buf[0] = uint2(value1, value2);
+}
+
+// CHECK-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 64, align: 32, elements: ![[elements_md:[0-9]+]]
+// CHECK-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 16, align: 32
+// CHECK-DAG: !DIBasicType(name: "min16uint", size: 16, align: 32, encoding: DW_ATE_unsigned)
+
+// CHECK16-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 32, align: 16, elements: ![[elements_md:[0-9]+]]
+// CHECK16-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK16-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 16, align: 16
+// CHECK16-DAG: !DIBasicType(name: "min16uint", size: 16, align: 16, encoding: DW_ATE_unsigned)
+

+ 50 - 0
tools/clang/test/HLSLFileCheck/dxil/debug/min16/min16uint_vec.hlsl

@@ -0,0 +1,50 @@
+// RUN: %dxc -E main -T cs_6_2 -Zi /Od %s | FileCheck %s
+// RUN: %dxc -E main -T cs_6_2 -Zi /Od %s -enable-16bit-types | FileCheck %s -check-prefix=CHECK16
+
+struct Foo
+{
+    min16uint3 m_A;
+    min16uint3 m_B;
+};
+
+StructuredBuffer<Foo> buf;
+RWTexture1D<uint4> out_buf;
+
+[numthreads(1, 1, 1)]
+[RootSignature("DescriptorTable(SRV(t0)), DescriptorTable(UAV(u0))")]
+void main()
+{
+    Foo foo = buf[0];
+    // foo.m_B.x
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 96, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 48, 16)
+
+    // foo.m_B.y
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 128, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 64, 16)
+
+    // foo.m_B.z
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 160, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 80, 16)
+
+    // foo.m_A.x
+    // CHECK-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+    // CHECK16-DAG: call void @llvm.dbg.value(metadata i16 %{{[0-9]+}}, i64 0, metadata !{{[0-9]+}}, metadata !{{[0-9]+}}), !dbg !{{[0-9]+}} ; var:"foo" !DIExpression(DW_OP_bit_piece, 0, 16)
+
+    min16int value1 = foo.m_B.x;
+    min16int value2 = foo.m_B.y;
+    min16int value3 = foo.m_B.z;
+    min16int value4 = foo.m_A.x;
+    out_buf[0] = uint4(value1, value2, value3, value4);
+}
+
+// CHECK-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 192, align: 32, elements: ![[elements_md:[0-9]+]]
+// CHECK-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 96, align: 32
+// CHECK-DAG: !DIBasicType(name: "min16uint", size: 16, align: 32, encoding: DW_ATE_unsigned)
+
+// CHECK16-DAG: !{{[0-9]+}} = !DICompositeType(tag: DW_TAG_structure_type, name: "Foo", file: !{{[0-9]+}}, line: {{[0-9]+}}, size: 96, align: 16, elements: ![[elements_md:[0-9]+]]
+// CHECK16-DAG: ![[elements_md]] = !{![[member_md:[0-9]+]]
+// CHECK16-DAG: ![[member_md]] = !DIDerivedType(tag: DW_TAG_member, name: "m_A", scope: !{{[0-9]+}}, file: !{{[0-9]+}}, line: {{[0-9]+}}, baseType: !{{[0-9]+}}, size: 48, align: 16
+// CHECK16-DAG: !DIBasicType(name: "min16uint", size: 16, align: 16, encoding: DW_ATE_unsigned)
+