Skip to content

Commit cb2be16

Browse files
author
Tim Corringham
committed
Amend template specialization DXASSERT conditions
Clang suppresses template specialization if a fatal error has been reported in order to reduce the risk of a cascade of secondary error diagnostics. However, DXC DXASSERTs if template specialization fails - even if that is due to an unrelated fatal error - which has the unintended result of hiding the fatal error and hence providing no indication of what the problem is. The DXASSERT conditions have been amended so they are no longer raised if a fatal error has been registered.
1 parent 1198c30 commit cb2be16

2 files changed

Lines changed: 43 additions & 13 deletions

File tree

tools/clang/lib/Sema/SemaHLSL.cpp

Lines changed: 21 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -850,11 +850,12 @@ GetOrCreateTemplateSpecialization(ASTContext &context, Sema &sema,
850850
if (specializationDecl->getInstantiatedFrom().isNull()) {
851851
// InstantiateClassTemplateSpecialization returns true if it finds an
852852
// error.
853-
DXVERIFY_NOMSG(false ==
854-
sema.InstantiateClassTemplateSpecialization(
855-
NoLoc, specializationDecl,
856-
TemplateSpecializationKind::TSK_ImplicitInstantiation,
857-
true));
853+
bool errorFound = sema.InstantiateClassTemplateSpecialization(
854+
NoLoc, specializationDecl,
855+
TemplateSpecializationKind::TSK_ImplicitInstantiation, true);
856+
// Template specialization is suppressed if a fatal error has already been
857+
// registered so don't assert in such cases.
858+
DXVERIFY_NOMSG(sema.Diags.hasFatalErrorOccurred() || !errorFound);
858859
}
859860
return context.getTemplateSpecializationType(
860861
TemplateName(templateDecl), templateArgs.data(), templateArgs.size(),
@@ -866,11 +867,12 @@ GetOrCreateTemplateSpecialization(ASTContext &context, Sema &sema,
866867
templateDecl, templateArgsForDecl.data(), templateArgsForDecl.size(),
867868
nullptr);
868869
// InstantiateClassTemplateSpecialization returns true if it finds an error.
869-
DXVERIFY_NOMSG(false ==
870-
sema.InstantiateClassTemplateSpecialization(
871-
NoLoc, specializationDecl,
872-
TemplateSpecializationKind::TSK_ImplicitInstantiation,
873-
true));
870+
bool errorFound = sema.InstantiateClassTemplateSpecialization(
871+
NoLoc, specializationDecl,
872+
TemplateSpecializationKind::TSK_ImplicitInstantiation, true);
873+
// Template specialization is suppressed if a fatal error has already been
874+
// registered so don't assert in such cases.
875+
DXVERIFY_NOMSG(sema.Diags.hasFatalErrorOccurred() || !errorFound);
874876
templateDecl->AddSpecialization(specializationDecl, InsertPos);
875877
specializationDecl->setImplicit(true);
876878

@@ -918,7 +920,9 @@ static QualType GetOrCreateMatrixSpecialization(
918920
DeclContext::lookup_result lookupResult =
919921
matrixSpecializationType->getAsCXXRecordDecl()->lookup(
920922
DeclarationName(&context.Idents.get(StringRef("h"))));
921-
DXASSERT(!lookupResult.empty(),
923+
// Template specialization is suppressed if a fatal error has been registered
924+
// so only assert if lookup failed for some other reason.
925+
DXASSERT(sema->Diags.hasFatalErrorOccurred() || !lookupResult.empty(),
922926
"otherwise matrix handle cannot be looked up");
923927
#endif
924928

@@ -953,7 +957,9 @@ GetOrCreateVectorSpecialization(ASTContext &context, Sema *sema,
953957
DeclContext::lookup_result lookupResult =
954958
vectorSpecializationType->getAsCXXRecordDecl()->lookup(
955959
DeclarationName(&context.Idents.get(StringRef("h"))));
956-
DXASSERT(!lookupResult.empty(),
960+
// Template specialization is suppressed if a fatal error has been registered
961+
// so only assert if lookup failed for some other reason.
962+
DXASSERT(sema->Diags.hasFatalErrorOccurred() || !lookupResult.empty(),
957963
"otherwise vector handle cannot be looked up");
958964
#endif
959965

@@ -981,7 +987,9 @@ GetOrCreateNodeOutputRecordSpecialization(ASTContext &context, Sema *sema,
981987
DeclContext::lookup_result lookupResult =
982988
specializationType->getAsCXXRecordDecl()->lookup(
983989
DeclarationName(&context.Idents.get(StringRef("h"))));
984-
DXASSERT(!lookupResult.empty(),
990+
// Template specialization is suppressed if a fatal error has been registered
991+
// so only assert if lookup failed for some other reason.
992+
DXASSERT(sema->Diags.hasFatalErrorOccurred() || !lookupResult.empty(),
985993
"otherwise *NodeOutputRecords handle cannot be looked up");
986994
#endif
987995

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// RUN: %dxc -T lib_6_8 -verify %s
2+
3+
// Clang suppresses template specialization if a fatal error has been
4+
// registered (this reduces the risk of a cascade of secondary errors).
5+
// However, DXC DXASSERTs if a template specialization fails - which
6+
// prevents the error diagnostic being generated.
7+
// We check here that a DXASSERT is no longer raised if a fatal error
8+
// has been registered, and that the error diagnostic is generated.
9+
10+
float a;
11+
12+
// the include file doesn't exist - this should produce a fatal error diagnostic
13+
// expected-error@+1 {{'a.h' file not found}}
14+
#include "a.h"
15+
16+
void b() {};
17+
18+
int3 c(int X) {
19+
// DXASSERT was triggered if include file a.h doesn't exist, and the error
20+
// diagnostic was not produced.
21+
return X.xxx;
22+
}

0 commit comments

Comments
 (0)