From adbaf8f23d7ef8c8e7786e8be706a47adce3f2ef Mon Sep 17 00:00:00 2001 From: ArielG-NV <159081215+ArielG-NV@users.noreply.github.com> Date: Fri, 19 Apr 2024 16:39:05 -0400 Subject: add `-ignore-capabilities` flag (#3984) `-ignore-capabilities` flag allows ignoring capability incompatibilities/discontinuity errors/warnings. We still process capabilities (needed for stdlib). Added to capability tests to ensure everything is working as intended. More will be added in the full stdlib capabilities implementation. --- source/slang/slang-check-decl.cpp | 39 ++++++++++++++++++++++++------------- source/slang/slang-check-impl.h | 11 ++++++++++- source/slang/slang-check-shader.cpp | 4 ++-- source/slang/slang-options.cpp | 2 ++ 4 files changed, 39 insertions(+), 17 deletions(-) (limited to 'source') diff --git a/source/slang/slang-check-decl.cpp b/source/slang/slang-check-decl.cpp index 131d30d98..d819121bc 100644 --- a/source/slang/slang-check-decl.cpp +++ b/source/slang/slang-check-decl.cpp @@ -9760,7 +9760,9 @@ namespace Slang // then the decl is using things that require conflicting set of capabilities, and we should diagnose an error. if (referencedDecl && decl) { - visitor->getSink()->diagnose( + diagnoseCapabilityErrors( + visitor->getSink(), + visitor->getOptionSet(), referenceLoc, Diagnostics::conflictingCapabilityDueToUseOfDecl, referencedDecl, @@ -9770,7 +9772,9 @@ namespace Slang } else if (decl) { - visitor->getSink()->diagnose( + diagnoseCapabilityErrors( + visitor->getSink(), + visitor->getOptionSet(), referenceLoc, Diagnostics::conflictingCapabilityDueToStatement, nodeCaps, @@ -9779,7 +9783,9 @@ namespace Slang } else { - visitor->getSink()->diagnose( + diagnoseCapabilityErrors( + visitor->getSink(), + visitor->getOptionSet(), referenceLoc, Diagnostics::conflictingCapabilityDueToStatementEnclosingFunc, nodeCaps, @@ -9807,8 +9813,11 @@ namespace Slang typedef SemanticsDeclReferenceVisitor> Base; const ProcessFunc& handleReferenceFunc; - CapabilityDeclReferenceVisitor(const ProcessFunc& processFunc, SemanticsContext const& outer) + + SemanticsContext& outerContext; + CapabilityDeclReferenceVisitor(const ProcessFunc& processFunc, SemanticsContext& outer) : handleReferenceFunc(processFunc) + , outerContext(outer) , SemanticsDeclReferenceVisitor>(outer) { } @@ -9834,7 +9843,7 @@ namespace Slang targetCap.join(bodyCap); if (targetCap.isInvalid()) { - Base::getSink()->diagnose(targetCase->body->loc, Diagnostics::conflictingCapabilityDueToStatement, bodyCap, "target_switch", oldCap); + diagnoseCapabilityErrors(Base::getSink(), outerContext.getOptionSet(), targetCase->body->loc, Diagnostics::conflictingCapabilityDueToStatement, bodyCap, "target_switch", oldCap); } for (auto& conjunction : targetCap.getExpandedAtoms()) set.unionWith(conjunction); @@ -9974,7 +9983,7 @@ namespace Slang auto stageCaps = CapabilitySet(Profile(entryPointAttr->stage).getCapabilityName()); if (declaredCaps.isIncompatibleWith(stageCaps)) { - getSink()->diagnose(funcDecl->loc, Diagnostics::stageIsInCompatibleWithCapabilityDefinition, funcDecl, stageCaps, declaredCaps); + diagnoseCapabilityErrors(getSink(), this->getOptionSet(), funcDecl->loc, Diagnostics::stageIsInCompatibleWithCapabilityDefinition, funcDecl, stageCaps, declaredCaps); } else { @@ -9994,7 +10003,9 @@ namespace Slang { if (funcDecl->inferredCapabilityRequirements != getAnyPlatformCapabilitySet()) { - getSink()->diagnose( + diagnoseCapabilityErrors( + getSink(), + this->getOptionSet(), funcDecl->loc, Diagnostics::missingCapabilityRequirementOnPublicDecl, funcDecl, funcDecl->inferredCapabilityRequirements); @@ -10110,7 +10121,7 @@ namespace Slang return defaultVis; } - void diagnoseCapabilityProvenance(DiagnosticSink* sink, Decl* decl, CapabilityAtom missingAtom) + void diagnoseCapabilityProvenance(CompilerOptionSet& optionSet, DiagnosticSink* sink, Decl* decl, CapabilityAtom missingAtom) { HashSet printedDecls; auto thisModule = getModuleDecl(decl); @@ -10141,7 +10152,7 @@ namespace Slang } if (declToPrint) { - sink->diagnose(declToPrint->loc, Diagnostics::seeDefinitionOf, declToPrint); + diagnoseCapabilityErrors(sink, optionSet, declToPrint->loc, Diagnostics::seeDefinitionOf, declToPrint); } } @@ -10164,14 +10175,14 @@ namespace Slang loc = refLoc; } else - sink->diagnose(refLoc, Diagnostics::seeDefinitionOf, "statement"); + diagnoseCapabilityErrors(sink, visitor->getOptionSet(), refLoc, Diagnostics::seeDefinitionOf, "statement"); } }); if (!refDecl) break; if (printedDecls.add(refDecl)) { - sink->diagnose(loc, Diagnostics::seeUsingOf, refDecl); + diagnoseCapabilityErrors(sink, visitor->getOptionSet(), loc, Diagnostics::seeUsingOf, refDecl); decl = refDecl; } else @@ -10220,7 +10231,7 @@ namespace Slang continue; if (decl->inferredCapabilityRequirements.isIncompatibleWith(atom)) { - getSink()->diagnose(decl->loc, Diagnostics::declHasDependenciesNotDefinedOnTarget, decl, atom); + diagnoseCapabilityErrors(getSink(), this->getOptionSet(), decl->loc, Diagnostics::declHasDependenciesNotDefinedOnTarget, decl, atom); diagnoseIncompatibleAtomProvenance(this, getSink(), decl, atom); return; } @@ -10279,10 +10290,10 @@ namespace Slang } } - getSink()->diagnose(decl->loc, diagnosticInfo, decl, missingAtom); + diagnoseCapabilityErrors(getSink(), this->getOptionSet(), decl->loc, diagnosticInfo, decl, missingAtom); // Print provenances. - diagnoseCapabilityProvenance(getSink(), decl, missingAtom); + diagnoseCapabilityProvenance(this->getOptionSet(), getSink(), decl, missingAtom); } } diff --git a/source/slang/slang-check-impl.h b/source/slang/slang-check-impl.h index 2f8565f7f..f0c6d693d 100644 --- a/source/slang/slang-check-impl.h +++ b/source/slang/slang-check-impl.h @@ -11,6 +11,14 @@ namespace Slang { + template + bool diagnoseCapabilityErrors(DiagnosticSink* sink, CompilerOptionSet& optionSet, P const& pos, DiagnosticInfo const& info, Args const&... args) + { + if (optionSet.getBoolOption(CompilerOptionName::IgnoreCapabilities)) + return false; + return sink->diagnose(pos, info, args...); + } + /// Should the given `decl` be treated as a static rather than instance declaration? bool isEffectivelyStatic( Decl* decl); @@ -793,6 +801,7 @@ namespace Slang {} SharedSemanticsContext* getShared() { return m_shared; } + CompilerOptionSet& getOptionSet() { return getShared()->getOptionSet(); } ASTBuilder* getASTBuilder() { return m_astBuilder; } DiagnosticSink* getSink() { return m_sink; } @@ -2768,7 +2777,7 @@ namespace Slang DeclVisibility getDeclVisibility(Decl* decl); - void diagnoseCapabilityProvenance(DiagnosticSink* sink, Decl* decl, CapabilityAtom missingAtom); + void diagnoseCapabilityProvenance(CompilerOptionSet& optionSet, DiagnosticSink* sink, Decl* decl, CapabilityAtom missingAtom); void _ensureAllDeclsRec( SemanticsDeclVisitorBase* visitor, diff --git a/source/slang/slang-check-shader.cpp b/source/slang/slang-check-shader.cpp index 77a57d71e..d4e8bda6f 100644 --- a/source/slang/slang-check-shader.cpp +++ b/source/slang/slang-check-shader.cpp @@ -519,7 +519,7 @@ namespace Slang targetCaps.join(stageCapabilitySet); if (targetCaps.isIncompatibleWith(entryPointFuncDecl->inferredCapabilityRequirements)) { - sink->diagnose(entryPointFuncDecl, Diagnostics::entryPointUsesUnavailableCapability, entryPointFuncDecl, entryPointFuncDecl->inferredCapabilityRequirements, targetCaps); + diagnoseCapabilityErrors(sink, linkage->m_optionSet, entryPointFuncDecl, Diagnostics::entryPointUsesUnavailableCapability, entryPointFuncDecl, entryPointFuncDecl->inferredCapabilityRequirements, targetCaps); auto& interredCapConjunctions = entryPointFuncDecl->inferredCapabilityRequirements.getExpandedAtoms(); // Find out what exactly is incompatible and print out a trace of provenance to @@ -533,7 +533,7 @@ namespace Slang { if (CapabilityConjunctionSet(inferredAtom).isIncompatibleWith(atom)) { - diagnoseCapabilityProvenance(sink, entryPointFuncDecl, inferredAtom); + diagnoseCapabilityProvenance(linkage->m_optionSet, sink, entryPointFuncDecl, inferredAtom); goto breakLabel; } } diff --git a/source/slang/slang-options.cpp b/source/slang/slang-options.cpp index 3f17d6d44..896388db0 100644 --- a/source/slang/slang-options.cpp +++ b/source/slang/slang-options.cpp @@ -289,6 +289,7 @@ void initCommandOptions(CommandOptions& options) { OptionKind::Language, "-lang", "-lang ", "Set the language for the following input files."}, { OptionKind::MatrixLayoutColumn, "-matrix-layout-column-major", nullptr, "Set the default matrix layout to column-major."}, { OptionKind::MatrixLayoutRow,"-matrix-layout-row-major", nullptr, "Set the default matrix layout to row-major."}, + { OptionKind::IgnoreCapabilities,"-ignore-capabilities", nullptr, "Do not warn or error if capabilities are violated"}, { OptionKind::ModuleName, "-module-name", "-module-name ", "Set the module name to use when compiling multiple .slang source files into a single module."}, { OptionKind::Output, "-o", "-o ", @@ -1682,6 +1683,7 @@ SlangResult OptionsParser::_parse( case OptionKind::VulkanUseEntryPointName: case OptionKind::VulkanUseGLLayout: case OptionKind::VulkanEmitReflection: + case OptionKind::IgnoreCapabilities: case OptionKind::DefaultImageFormatUnknown: case OptionKind::Obfuscate: case OptionKind::OutputIncludes: -- cgit v1.2.3