diff options
| author | Yong He <yonghe@outlook.com> | 2023-02-07 18:36:35 -0800 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2023-02-07 18:36:35 -0800 |
| commit | 4be623c52a6518eb86756a0369706c1d6670f6bb (patch) | |
| tree | c24f54e34db9f1f02c2d51808b15121eba9195a9 | |
| parent | 101f164b036d0c1c012243df69179559b6f40fb8 (diff) | |
Arithmetic simplifications and more IR clean up logic. (#2632)
54 files changed, 1450 insertions, 460 deletions
diff --git a/build/visual-studio/slang/slang.vcxproj b/build/visual-studio/slang/slang.vcxproj index 00b7076dd..979ee4e96 100644 --- a/build/visual-studio/slang/slang.vcxproj +++ b/build/visual-studio/slang/slang.vcxproj @@ -414,6 +414,7 @@ IF EXIST ..\..\..\external\slang-glslang\bin\windows-aarch64\release\slang-glsla <ClInclude Include="..\..\..\source\slang\slang-ir-restructure.h" />
<ClInclude Include="..\..\..\source\slang\slang-ir-sccp.h" />
<ClInclude Include="..\..\..\source\slang\slang-ir-simplify-cfg.h" />
+ <ClInclude Include="..\..\..\source\slang\slang-ir-simplify-for-emit.h" />
<ClInclude Include="..\..\..\source\slang\slang-ir-single-return.h" />
<ClInclude Include="..\..\..\source\slang\slang-ir-specialize-arrays.h" />
<ClInclude Include="..\..\..\source\slang\slang-ir-specialize-buffer-load-arg.h" />
@@ -599,6 +600,7 @@ IF EXIST ..\..\..\external\slang-glslang\bin\windows-aarch64\release\slang-glsla <ClCompile Include="..\..\..\source\slang\slang-ir-restructure.cpp" />
<ClCompile Include="..\..\..\source\slang\slang-ir-sccp.cpp" />
<ClCompile Include="..\..\..\source\slang\slang-ir-simplify-cfg.cpp" />
+ <ClCompile Include="..\..\..\source\slang\slang-ir-simplify-for-emit.cpp" />
<ClCompile Include="..\..\..\source\slang\slang-ir-single-return.cpp" />
<ClCompile Include="..\..\..\source\slang\slang-ir-specialize-arrays.cpp" />
<ClCompile Include="..\..\..\source\slang\slang-ir-specialize-buffer-load-arg.cpp" />
diff --git a/build/visual-studio/slang/slang.vcxproj.filters b/build/visual-studio/slang/slang.vcxproj.filters index f79d322ae..e151f6c4f 100644 --- a/build/visual-studio/slang/slang.vcxproj.filters +++ b/build/visual-studio/slang/slang.vcxproj.filters @@ -348,6 +348,9 @@ <ClInclude Include="..\..\..\source\slang\slang-ir-simplify-cfg.h">
<Filter>Header Files</Filter>
</ClInclude>
+ <ClInclude Include="..\..\..\source\slang\slang-ir-simplify-for-emit.h">
+ <Filter>Header Files</Filter>
+ </ClInclude>
<ClInclude Include="..\..\..\source\slang\slang-ir-single-return.h">
<Filter>Header Files</Filter>
</ClInclude>
@@ -899,6 +902,9 @@ <ClCompile Include="..\..\..\source\slang\slang-ir-simplify-cfg.cpp">
<Filter>Source Files</Filter>
</ClCompile>
+ <ClCompile Include="..\..\..\source\slang\slang-ir-simplify-for-emit.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
<ClCompile Include="..\..\..\source\slang\slang-ir-single-return.cpp">
<Filter>Source Files</Filter>
</ClCompile>
diff --git a/source/slang/hlsl.meta.slang b/source/slang/hlsl.meta.slang index f5b138f25..6c7a2c1d2 100644 --- a/source/slang/hlsl.meta.slang +++ b/source/slang/hlsl.meta.slang @@ -4793,7 +4793,7 @@ void __executeCallable(uint shaderIndex, int payloadLocation); __generic<Payload> __target_intrinsic(__glslRayTracing, "$XC") [__readNone] -int __callablePayloadLocation(Payload payload); +int __callablePayloadLocation(__ref Payload payload); // Now we provide a hard-coded definition of `CallShader()` for GLSL-based // targets, which maps the generic HLSL operation into the non-generic @@ -4848,7 +4848,7 @@ void __traceRay( __generic<Payload> __target_intrinsic(__glslRayTracing, "$XP") [__readNone] -int __rayPayloadLocation(Payload payload); +int __rayPayloadLocation(__ref Payload payload); __generic<payload_t> __specialized_for_target(glsl) @@ -5678,7 +5678,7 @@ struct VkSubpassInputMS<T> // We access the HitObjectAttributes via this function for the desired type, and it acts *as if* it's just an access // to the global t. [ForceInline] -__ref T __hitObjectAttributes<T>() +Ref<T> __hitObjectAttributes<T>() { [__vulkanHitObjectAttributes] static T t; @@ -5691,7 +5691,7 @@ __ref T __hitObjectAttributes<T>() __generic<Payload> __target_intrinsic(__glslRayTracing, "$XH") [__readNone] -int __hitObjectAttributesLocation(Payload payload); +int __hitObjectAttributesLocation(__ref Payload payload); /// Immutable data type representing a ray hit or a miss. Can be used to invoke hit or miss shading, /// or as a key in ReorderThread. Created by one of several methods described below. HitObject diff --git a/source/slang/slang-ast-expr.h b/source/slang/slang-ast-expr.h index 9fdc10807..d49db89a2 100644 --- a/source/slang/slang-ast-expr.h +++ b/source/slang/slang-ast-expr.h @@ -268,6 +268,13 @@ class SwizzleExpr: public Expr SourceLoc memberOpLoc; }; +// An operation to convert an l-value to a reference type. +class MakeRefExpr : public Expr +{ + SLANG_AST_CLASS(MakeRefExpr) + Expr* base = nullptr; +}; + // A dereference of a pointer or pointer-like type class DerefExpr: public Expr { diff --git a/source/slang/slang-ast-support-types.h b/source/slang/slang-ast-support-types.h index 21611bcb1..5fd9df400 100644 --- a/source/slang/slang-ast-support-types.h +++ b/source/slang/slang-ast-support-types.h @@ -78,6 +78,7 @@ namespace Slang // Conversion from a buffer to the type it carries needs to add a minimal // extra cost, just so we can distinguish an overload on `ConstantBuffer<Foo>` // from one on `Foo` + kConversionCost_GetRef = 5, kConversionCost_ImplicitDereference = 10, // Conversions based on explicit sub-typing relationships are the cheapest diff --git a/source/slang/slang-check-conversion.cpp b/source/slang/slang-check-conversion.cpp index 6decce625..71231b9e5 100644 --- a/source/slang/slang-check-conversion.cpp +++ b/source/slang/slang-check-conversion.cpp @@ -642,11 +642,6 @@ namespace Slang return true; } - if (auto refType = as<RefType>(toType)) - { - return _coerce(refType->getValueType(), outToExpr, fromType, fromExpr, outCost); - } - // If both are string types we assume they are convertable in both directions if (as<StringTypeBase>(fromType) && as<StringTypeBase>(toType)) { @@ -860,6 +855,63 @@ namespace Slang return true; } + if (auto refType = as<RefType>(toType)) + { + if (!refType->getValueType()->equals(fromType)) + return false; + if (!fromExpr->type.isLeftValue) + return false; + + ConversionCost subCost = kConversionCost_GetRef; + + MakeRefExpr* refExpr = nullptr; + if (outToExpr) + { + refExpr = m_astBuilder->create<MakeRefExpr>(); + refExpr->base = fromExpr; + refExpr->type = QualType(refType); + refExpr->type.isLeftValue = false; + *outToExpr = refExpr; + } + if (outCost) + *outCost = subCost; + return true; + } + + + // Allow implicit dereferencing a reference type. + if (auto fromRefType = as<RefType>(fromType)) + { + auto fromValueType = fromRefType->getValueType(); + + // If we convert, e.g., `ConstantBuffer<A> to `A`, we will allow + // subsequent conversion of `A` to `B` if such a conversion + // is possible. + // + ConversionCost subCost = kConversionCost_None; + + Expr* openRefExpr = nullptr; + if (outToExpr) + { + openRefExpr = maybeOpenRef(fromExpr); + } + + if (!_coerce( + toType, + outToExpr, + fromValueType, + openRefExpr, + &subCost)) + { + return false; + } + + if (outCost) + *outCost = subCost + kConversionCost_ImplicitDereference; + return true; + } + + // The main general-purpose approach for conversion is // using suitable marked initializer ("constructor") // declarations on the target type. diff --git a/source/slang/slang-check-expr.cpp b/source/slang/slang-check-expr.cpp index 7e2bc3822..7d546e60b 100644 --- a/source/slang/slang-check-expr.cpp +++ b/source/slang/slang-check-expr.cpp @@ -1863,6 +1863,7 @@ namespace Slang Expr* SemanticsVisitor::checkAssignWithCheckedOperands(AssignExpr* expr) { + expr->left = maybeOpenRef(expr->left); auto type = expr->left->type; auto right = maybeOpenRef(expr->right); expr->right = coerce(type, right); diff --git a/source/slang/slang-check-impl.h b/source/slang/slang-check-impl.h index ac5fc8392..719706635 100644 --- a/source/slang/slang-check-impl.h +++ b/source/slang/slang-check-impl.h @@ -1928,6 +1928,7 @@ namespace Slang } CASE(DerefExpr) + CASE(MakeRefExpr) CASE(MatrixSwizzleExpr) CASE(SwizzleExpr) CASE(OverloadedExpr) diff --git a/source/slang/slang-emit-c-like.cpp b/source/slang/slang-emit-c-like.cpp index 160585e26..c664449e5 100644 --- a/source/slang/slang-emit-c-like.cpp +++ b/source/slang/slang-emit-c-like.cpp @@ -1082,6 +1082,7 @@ bool CLikeSourceEmitter::shouldFoldInstIntoUseSites(IRInst* inst) case kIROp_Param: case kIROp_Func: case kIROp_Alloca: + case kIROp_Store: return false; // Never fold these, because their result cannot be computed @@ -1997,17 +1998,6 @@ void CLikeSourceEmitter::defaultEmitInstExpr(IRInst* inst, const EmitOpInfo& inO } break; - case kIROp_Store: - { - auto prec = getInfo(EmitOp::Assign); - needClose = maybeEmitParens(outerPrec, prec); - - emitDereferenceOperand(inst->getOperand(0), leftSide(outerPrec, prec)); - m_writer->emit(" = "); - emitOperand(inst->getOperand(1), rightSide(prec, outerPrec)); - } - break; - case kIROp_Call: { emitCallExpr((IRCall*)inst, outerPrec); @@ -2393,6 +2383,22 @@ void CLikeSourceEmitter::_emitInst(IRInst* inst) } break; + case kIROp_Store: + { + if (inst->getPrevInst() == inst->getOperand(0) && inst->getOperand(0)->getOp() == kIROp_Var) + { + // If we are storing into a var that is defined right before the store, we have + // already folded the store in the initialization of the var, so we can skip here. + break; + } + auto prec = getInfo(EmitOp::Assign); + emitDereferenceOperand(inst->getOperand(0), leftSide(getInfo(EmitOp::General), prec)); + m_writer->emit(" = "); + emitOperand(inst->getOperand(1), rightSide(prec, getInfo(EmitOp::General))); + m_writer->emit(";\n"); + } + break; + case kIROp_Param: // Don't emit parameters, since they are declared as part of the function. break; @@ -3321,6 +3327,15 @@ void CLikeSourceEmitter::emitVar(IRVar* varDecl) emitLayoutSemantics(varDecl); + if (auto store = as<IRStore>(varDecl->getNextInst())) + { + if (store->getPtr() == varDecl) + { + m_writer->emit(" = "); + emitOperand(store->getVal(), getInfo(EmitOp::General)); + } + } + m_writer->emit(";\n"); } diff --git a/source/slang/slang-emit-source-writer.cpp b/source/slang/slang-emit-source-writer.cpp index bed9a2dbc..7692bd0ec 100644 --- a/source/slang/slang-emit-source-writer.cpp +++ b/source/slang/slang-emit-source-writer.cpp @@ -247,8 +247,21 @@ void SourceWriter::emit(double value) stream.setf(std::ios::fixed, std::ios::floatfield); stream.precision(20); stream << value; - - emit(stream.str().c_str()); + auto str = stream.str(); + auto slice = UnownedStringSlice(str.c_str()); + // Remove redundant trailing 0s. + if (slice.end() > slice.begin()) + { + auto lastChar = slice.end() - 1; + while (lastChar > slice.begin() && *lastChar == '0') + lastChar--; + if (*lastChar == '.') + lastChar++; + if (lastChar > slice.end() - 1) + lastChar = slice.end() - 1; + slice = slice.subString(0, lastChar - slice.begin() + 1); + } + emit(slice); } void SourceWriter::advanceToSourceLocationIfValid(const SourceLoc& sourceLocation) diff --git a/source/slang/slang-emit.cpp b/source/slang/slang-emit.cpp index 3d923179c..2ef0a5647 100644 --- a/source/slang/slang-emit.cpp +++ b/source/slang/slang-emit.cpp @@ -54,6 +54,7 @@ #include "slang-ir-liveness.h" #include "slang-ir-glsl-liveness.h" #include "slang-ir-string-hash.h" +#include "slang-ir-simplify-for-emit.h" #include "slang-legalize-types.h" #include "slang-lower-to-ir.h" #include "slang-mangle.h" @@ -1008,6 +1009,9 @@ SlangResult CodeGenContext::emitEntryPointsSourceFromIR(ComPtr<IArtifact>& outAr linkedIR)); auto irModule = linkedIR.module; + + // Perform final simplifications to help emit logic to generate more compact code. + simplifyForEmit(irModule); metadata = linkedIR.metadata; @@ -1015,15 +1019,6 @@ SlangResult CodeGenContext::emitEntryPointsSourceFromIR(ComPtr<IArtifact>& outAr // passes have been performed, we can emit target code from // the IR module. // - // TODO: do we want to emit directly from IR, or translate the - // IR back into AST for emission? -#if 0 - { - StringBuilder sb; - StringWriter writer(&sb, Slang::WriterFlag::AutoFlush); - dumpIR(irModule, getIRDumpOptions(), sourceManager, &writer); - } -#endif sourceEmitter->emitModule(irModule, sink); } diff --git a/source/slang/slang-intrinsic-expand.cpp b/source/slang/slang-intrinsic-expand.cpp index 64ef4e761..de3396efb 100644 --- a/source/slang/slang-intrinsic-expand.cpp +++ b/source/slang/slang-intrinsic-expand.cpp @@ -735,14 +735,10 @@ const char* IntrinsicExpandContext::_emitSpecial(const char* cursor) Index argIndex = 0; SLANG_RELEASE_ASSERT(m_argCount > argIndex); auto arg = m_args[argIndex].get(); - auto argLoad = as<IRLoad>(arg); - SLANG_RELEASE_ASSERT(argLoad); - - auto argVar = argLoad->getOperand(0); // Find the associated decoration IRDecoration* foundDecoration = nullptr; - for (auto decoration : argVar->getDecorations()) + for (auto decoration : arg->getDecorations()) { const auto curKind = LocationTracker::getKindFromDecoration(decoration); if (curKind == kind) @@ -755,7 +751,7 @@ const char* IntrinsicExpandContext::_emitSpecial(const char* cursor) // Must have found the decoration SLANG_ASSERT(foundDecoration); - const auto location = m_emitter->getLocationTracker().getValue(kind, argVar, foundDecoration); + const auto location = m_emitter->getLocationTracker().getValue(kind, arg, foundDecoration); m_writer->emit(location); } } diff --git a/source/slang/slang-ir-autodiff-fwd.cpp b/source/slang/slang-ir-autodiff-fwd.cpp index 16b7a977c..a45a3abf9 100644 --- a/source/slang/slang-ir-autodiff-fwd.cpp +++ b/source/slang/slang-ir-autodiff-fwd.cpp @@ -1162,6 +1162,8 @@ InstPair ForwardDiffTranscriber::transcribeFuncHeader(IRBuilder* inBuilder, IRFu inBuilder->addForwardDerivativeDecoration(origFunc, diffFunc); } + inBuilder->addFloatingModeOverrideDecoration(diffFunc, FloatingPointMode::Fast); + FuncBodyTranscriptionTask task; task.type = FuncBodyTranscriptionTaskType::Forward; task.originalFunc = origFunc; diff --git a/source/slang/slang-ir-autodiff-rev.cpp b/source/slang/slang-ir-autodiff-rev.cpp index fed53b037..702f9819a 100644 --- a/source/slang/slang-ir-autodiff-rev.cpp +++ b/source/slang/slang-ir-autodiff-rev.cpp @@ -12,6 +12,7 @@ #include "slang-ir-addr-inst-elimination.h" #include "slang-ir-eliminate-multilevel-break.h" #include "slang-ir-init-local-var.h" +#include "slang-ir-redundancy-removal.h" namespace Slang { @@ -305,7 +306,14 @@ namespace Slang IRFunc* primalFunc = origFunc; maybeMigrateDifferentiableDictionaryFromDerivativeFunc(inBuilder, origFunc); - differentiableTypeConformanceContext.setFunc(origFunc); + + // The original func may not have a type dictionary if it is not originally marked as + // differentiable, in this case we would have already pulled the necessary types from + // the user-provided derivative function, so we are still fine. + if (origFunc->findDecoration<IRDifferentiableTypeDictionaryDecoration>()) + { + differentiableTypeConformanceContext.setFunc(origFunc); + } auto diffFunc = builder.createFunc(); @@ -334,7 +342,7 @@ namespace Slang builder.setInsertBefore(diffFunc->getFirstDecorationOrChild()); cloneInst(&cloneEnv, &builder, dictDecor); } - + builder.addFloatingModeOverrideDecoration(diffFunc, FloatingPointMode::Fast); return InstPair(primalFunc, diffFunc); } @@ -588,43 +596,6 @@ namespace Slang return result; } - void eliminateRedundantLoad(IRFunc* func) - { - for (auto block : func->getBlocks()) - { - for (auto inst = block->getFirstInst(); inst;) - { - auto nextInst = inst->getNextInst(); - if (auto load = as<IRLoad>(inst)) - { - for (auto prev = inst->getPrevInst(); prev; prev = prev->getPrevInst()) - { - if (auto store = as<IRStore>(prev)) - { - if (store->getPtr() == load->getPtr()) - { - // If the load is preceeded by a store without any side-effect insts in-between, remove the load. - auto value = store->getVal(); - load->replaceUsesWith(value); - load->removeAndDeallocate(); - break; - } - } - else if (as<IRCall>(prev)) - { - break; - } - else if (prev->mightHaveSideEffects()) - { - break; - } - } - } - inst = nextInst; - } - } - } - // Create a copy of originalFunc's forward derivative in the same generic context (if any) of // `diffPropagateFunc`. IRFunc* BackwardDiffTranscriberBase::generateNewForwardDerivativeForFunc( @@ -669,7 +640,7 @@ namespace Slang primalOuterParent->removeAndDeallocate(); // Remove redundant loads since they interfere with transposition logic. - eliminateRedundantLoad(fwdDiffFunc); + eliminateRedundantLoadStore(fwdDiffFunc); // Migrate the new forward derivative function into the generic parent of `diffPropagateFunc`. if (auto fwdParentGeneric = as<IRGeneric>(findOuterGeneric(fwdDiffFunc))) @@ -976,13 +947,16 @@ namespace Slang { // Create dOut param. auto diffParam = builder->emitParam(diffType); + copyNameHintDecoration(diffParam, fwdParam); result.propagateFuncParams.Add(diffParam); primalRefReplacement = builder->emitParam(builder->getOutType(primalType)); + copyNameHintDecoration(primalRefReplacement, fwdParam); // Create a local var for read access in pre-transpose code. // This will the var from which we will fetch the final resulting derivative // after transposition. auto tempVar = nextBlockBuilder.emitVar(diffType); + copyNameHintDecoration(tempVar, fwdParam); nextBlockBuilder.markInstAsDifferential(tempVar, diffPairType); // Initialize the var with input diff param at start. @@ -999,11 +973,13 @@ namespace Slang else { primalRefReplacement = builder->emitParam(outType); + copyNameHintDecoration(primalRefReplacement, fwdParam); } result.primalFuncParams.Add(primalRefReplacement); // Create a local var for the out param for the primal part of the prop func. auto tempPrimalVar = nextBlockBuilder.emitVar(outType->getValueType()); + copyNameHintDecoration(tempPrimalVar, fwdParam); result.mapPrimalSpecificParamToReplacementInPropFunc[primalRefReplacement] = tempPrimalVar; instsToRemove.Add(fwdParam); @@ -1023,10 +999,13 @@ namespace Slang // Create an in param for the prop func. auto propParam = builder->emitParam(inoutType->getValueType()); + copyNameHintDecoration(propParam, fwdParam); result.propagateFuncParams.Add(propParam); // Create a local var for the out param for the primal part of the prop func. auto tempPrimalVar = nextBlockBuilder.emitVar(inoutType->getValueType()); + copyNameHintDecoration(tempPrimalVar, fwdParam); + result.propagateFuncSpecificPrimalInsts.add(tempPrimalVar); auto storeInst = nextBlockBuilder.emitStore(tempPrimalVar, propParam); result.propagateFuncSpecificPrimalInsts.add(storeInst); @@ -1054,8 +1033,11 @@ namespace Slang // Create inout version. auto inoutDiffPairType = builder->getInOutType(diffPairType); primalRefReplacement = builder->emitParam(primalType); + copyNameHintDecoration(primalRefReplacement, fwdParam); + result.primalFuncParams.Add(primalRefReplacement); auto propParam = builder->emitParam(inoutDiffPairType); + copyNameHintDecoration(propParam, fwdParam); result.propagateFuncParams.Add(propParam); // A reference to this parameter from the diff blocks should be replaced with a load @@ -1085,9 +1067,11 @@ namespace Slang // Process differentiable inout parameters. auto primalParam = builder->emitParam(builder->getInOutType(primalType)); + copyNameHintDecoration(primalParam, fwdParam); result.primalFuncParams.Add(primalParam); auto diffParam = builder->emitParam(inoutType); + copyNameHintDecoration(diffParam, fwdParam); result.propagateFuncParams.Add(diffParam); // Primal references to this param is the new primal param. @@ -1102,6 +1086,7 @@ namespace Slang // Create a local var for diff read access. auto diffVar = nextBlockBuilder.emitVar(diffType); + copyNameHintDecoration(diffVar, fwdParam); result.propagateFuncSpecificPrimalInsts.add(diffVar); diffBuilder.markInstAsDifferential(diffVar, diffPairType); diffRefReplacement = diffVar; @@ -1114,6 +1099,8 @@ namespace Slang // Create a local var for diff write access. auto diffWriteVar = nextBlockBuilder.emitVar(diffType); + copyNameHintDecoration(diffWriteVar, fwdParam); + // Initialize write var to 0. auto writeStore = nextBlockBuilder.emitStore(diffWriteVar, initDiff); result.propagateFuncSpecificPrimalInsts.add(writeStore); @@ -1122,6 +1109,8 @@ namespace Slang // Create a local var for the primal logic in the propagate func. auto primalVar = nextBlockBuilder.emitVar(primalType); + copyNameHintDecoration(primalVar, fwdParam); + result.propagateFuncSpecificPrimalInsts.add(primalVar); auto initPrimalVal = nextBlockBuilder.emitDifferentialPairGetPrimal(loadedParam); result.propagateFuncSpecificPrimalInsts.add(initPrimalVal); @@ -1213,11 +1202,13 @@ namespace Slang SLANG_ASSERT(dOutParamType); dOutParam = builder->emitParam(dOutParamType); + builder->addNameHintDecoration(dOutParam, UnownedStringSlice("_s_dOut")); result.propagateFuncParams.Add(dOutParam); } // Add a parameter for intermediate val. auto ctxParam = builder->emitParam(as<IRFuncType>(diffFunc->getDataType())->getParamType(paramCount - 1)); + builder->addNameHintDecoration(ctxParam, UnownedStringSlice("_s_diff_ctx")); result.primalFuncParams.Add(ctxParam); result.propagateFuncParams.Add(ctxParam); result.dOutParam = dOutParam; diff --git a/source/slang/slang-ir-autodiff-unzip.cpp b/source/slang/slang-ir-autodiff-unzip.cpp index be20d8aa8..3e7e346d2 100644 --- a/source/slang/slang-ir-autodiff-unzip.cpp +++ b/source/slang/slang-ir-autodiff-unzip.cpp @@ -295,6 +295,7 @@ struct ExtractPrimalFuncContext auto oldIntermediateParam = func->getLastParam(); auto outIntermediary = builder.emitParam(builder.getInOutType((IRType*)intermediateType)); + oldIntermediateParam->transferDecorationsTo(outIntermediary); primalParams.Add(outIntermediary); oldIntermediateParam->replaceUsesWith(outIntermediary); oldIntermediateParam->removeAndDeallocate(); @@ -473,15 +474,34 @@ IRFunc* DiffUnzipPass::extractPrimalFunc( if (inst->getOp() == kIROp_Var) { // This is a var for intermediate context. - auto valType = cast<IRPtrTypeBase>(inst->getFullType())->getValueType(); - auto val = builder.emitFieldExtract( - valType, - intermediateVar, - structKeyDecor->getStructKey()); - auto tempVar = - builder.emitVar(valType); - builder.emitStore(tempVar, val); - inst->replaceUsesWith(tempVar); + // Replace all loads of the var with a field extract. + // Other type of uses will get a temp var that stores a copy of the field. + while (auto use = inst->firstUse) + { + if (as<IRDecoration>(use->getUser())) + { + use->set(builder.getVoidValue()); + continue; + } + builder.setInsertBefore(use->getUser()); + auto valType = cast<IRPtrTypeBase>(inst->getFullType())->getValueType(); + auto val = builder.emitFieldExtract( + valType, + intermediateVar, + structKeyDecor->getStructKey()); + if (use->getUser()->getOp() == kIROp_Load) + { + use->getUser()->replaceUsesWith(val); + use->getUser()->removeAndDeallocate(); + } + else + { + auto tempVar = + builder.emitVar(valType); + builder.emitStore(tempVar, val); + use->set(tempVar); + } + } } else { diff --git a/source/slang/slang-ir-autodiff.cpp b/source/slang/slang-ir-autodiff.cpp index fdaff4960..f38bdfdbd 100644 --- a/source/slang/slang-ir-autodiff.cpp +++ b/source/slang/slang-ir-autodiff.cpp @@ -256,6 +256,11 @@ IRInst* DifferentialPairTypeBuilder::_createDiffPairType(IRType* origBaseType, I builder.setInsertBefore(diffType); auto pairStructType = builder.createStructType(); + StringBuilder nameBuilder; + nameBuilder << "DiffPair_"; + getTypeNameHint(nameBuilder, origBaseType); + builder.addNameHintDecoration(pairStructType, nameBuilder.ToString().getUnownedSlice()); + builder.createStructField(pairStructType, _getOrCreatePrimalStructKey(), origBaseType); builder.createStructField(pairStructType, _getOrCreateDiffStructKey(), (IRType*)diffType); return pairStructType; diff --git a/source/slang/slang-ir-dce.cpp b/source/slang/slang-ir-dce.cpp index 33e5b3cb4..337caa246 100644 --- a/source/slang/slang-ir-dce.cpp +++ b/source/slang/slang-ir-dce.cpp @@ -3,6 +3,7 @@ #include "slang-ir.h" #include "slang-ir-insts.h" +#include "slang-ir-util.h" namespace Slang { @@ -16,6 +17,7 @@ struct DeadCodeEliminationContext // `eliminateDeadCode` function. // IRModule* module; + IRDeadCodeEliminationOptions options; // If we removed an inst, there may be still "weak references" to the inst. @@ -129,6 +131,9 @@ struct DeadCodeEliminationContext auto inst = workList.getLast(); workList.removeLast(); + if (!isChildInstOf(inst, root)) + continue; + // At this point we know that `inst` is live, // and we want to start considering which other // instructions must be live because of that @@ -426,7 +431,6 @@ bool eliminateDeadCode( DeadCodeEliminationContext context; context.module = module; context.options = options; - return context.processModule(); } @@ -437,7 +441,6 @@ bool eliminateDeadCode( DeadCodeEliminationContext context; context.module = root->getModule(); context.options = options; - return context.processInst(root); } diff --git a/source/slang/slang-ir-inst-defs.h b/source/slang/slang-ir-inst-defs.h index 1cb839751..26a92a17a 100644 --- a/source/slang/slang-ir-inst-defs.h +++ b/source/slang/slang-ir-inst-defs.h @@ -797,6 +797,9 @@ INST(HighLevelDeclDecoration, highLevelDecl, 1, 0) /* Differentiable Type Dictionary */ INST(DifferentiableTypeDictionaryDecoration, DifferentiableTypeDictionaryDecoration, 0, PARENT) + /// Overrides the floating mode for the target function + INST(FloatingPointModeOverrideDecoration, FloatingPointModeOverride, 1, 0) + /// Marks a struct type as being used as a structured buffer block. /// Recognized by SPIRV-emit pass so we can emit a SPIRV `BufferBlock` decoration. INST(SPIRVBufferBlockDecoration, spvBufferBlock, 0, 0) diff --git a/source/slang/slang-ir-insts.h b/source/slang/slang-ir-insts.h index d1374477f..fad20e900 100644 --- a/source/slang/slang-ir-insts.h +++ b/source/slang/slang-ir-insts.h @@ -846,6 +846,13 @@ struct IRDifferentiableTypeDictionaryDecoration : IRDecoration IR_LEAF_ISA(DifferentiableTypeDictionaryDecoration) }; +struct IRFloatingModeOverrideDecoration : IRDecoration +{ + IR_LEAF_ISA(FloatingPointModeOverrideDecoration) + + FloatingPointMode getFloatingPointMode() { return (FloatingPointMode)cast<IRIntLit>(getOperand(0))->getValue(); } +}; + // An instruction that specializes another IR value // (representing a generic) to a particular set of generic arguments // (instructions representing types, witness tables, etc.) @@ -2835,6 +2842,8 @@ public: // Add a differentiable type entry to the appropriate dictionary. IRInst* addDifferentiableTypeEntry(IRInst* dictDecoration, IRInst* irType, IRInst* conformanceWitness); + IRInst* addFloatingModeOverrideDecoration(IRInst* dest, FloatingPointMode mode); + IRInst* emitSpecializeInst( IRType* type, IRInst* genericVal, diff --git a/source/slang/slang-ir-peephole.cpp b/source/slang/slang-ir-peephole.cpp index fd0b4577a..65b4adcac 100644 --- a/source/slang/slang-ir-peephole.cpp +++ b/source/slang/slang-ir-peephole.cpp @@ -10,6 +10,7 @@ struct PeepholeContext : InstPassBase {} bool changed = false; + FloatingPointMode floatingPointMode = FloatingPointMode::Precise; bool tryFoldElementExtractFromUpdateInst(IRInst* inst) { @@ -96,8 +97,158 @@ struct PeepholeContext : InstPassBase return false; } + bool isZero(IRInst* inst) + { + switch (inst->getOp()) + { + case kIROp_IntLit: + return as<IRIntLit>(inst)->getValue() == 0; + case kIROp_FloatLit: + return as<IRFloatLit>(inst)->getValue() == 0.0; + case kIROp_MakeVector: + case kIROp_MakeVectorFromScalar: + case kIROp_MakeMatrix: + case kIROp_MakeMatrixFromScalar: + case kIROp_MatrixReshape: + case kIROp_VectorReshape: + { + for (UInt i = 0; i < inst->getOperandCount(); i++) + { + if (!isZero(inst->getOperand(i))) + { + return false; + } + } + return true; + } + case kIROp_CastIntToFloat: + case kIROp_CastFloatToInt: + return isZero(inst->getOperand(0)); + default: + return false; + } + } + + bool isOne(IRInst* inst) + { + switch (inst->getOp()) + { + case kIROp_IntLit: + return as<IRIntLit>(inst)->getValue() == 1; + case kIROp_FloatLit: + return as<IRFloatLit>(inst)->getValue() == 1.0; + case kIROp_MakeVector: + case kIROp_MakeVectorFromScalar: + case kIROp_MakeMatrix: + case kIROp_MakeMatrixFromScalar: + case kIROp_MatrixReshape: + case kIROp_VectorReshape: + { + for (UInt i = 0; i < inst->getOperandCount(); i++) + { + if (!isOne(inst->getOperand(i))) + { + return false; + } + } + return true; + } + case kIROp_CastIntToFloat: + case kIROp_CastFloatToInt: + return isOne(inst->getOperand(0)); + default: + return false; + } + } + + bool tryOptimizeArithmeticInst(IRInst* inst) + { + bool allowUnsafeOptimizations = + (floatingPointMode == FloatingPointMode::Fast || + isIntegralScalarOrCompositeType(inst->getDataType())); + + auto tryReplace = [&](IRInst* replacement) -> bool + { + if (replacement->getFullType() != inst->getFullType()) + { + // If the operand type is different from result type, + // we try to convert for some known cases. + if (auto vectorType = as<IRVectorType>(inst->getFullType())) + { + if (vectorType->getElementType() != replacement->getFullType()) + return false; + IRBuilder builder(sharedBuilderStorage); + builder.setInsertBefore(inst); + replacement = builder.emitMakeVectorFromScalar(inst->getFullType(), replacement); + } + else + { + return false; + } + } + + inst->replaceUsesWith(replacement); + inst->removeAndDeallocate(); + return true; + }; + + switch (inst->getOp()) + { + case kIROp_Add: + if (isZero(inst->getOperand(0))) + { + return tryReplace(inst->getOperand(1)); + } + else if (isZero(inst->getOperand(1))) + { + return tryReplace(inst->getOperand(0)); + } + break; + case kIROp_Sub: + if (isZero(inst->getOperand(1))) + { + return tryReplace(inst->getOperand(0)); + } + break; + case kIROp_Mul: + if (isOne(inst->getOperand(0))) + { + return tryReplace(inst->getOperand(1)); + } + else if (isOne(inst->getOperand(1))) + { + return tryReplace(inst->getOperand(0)); + } + else if (allowUnsafeOptimizations && isZero(inst->getOperand(0))) + { + return tryReplace(inst->getOperand(0)); + } + else if (allowUnsafeOptimizations && isZero(inst->getOperand(1))) + { + return tryReplace(inst->getOperand(1)); + } + break; + case kIROp_Div: + if (allowUnsafeOptimizations && isZero(inst->getOperand(0))) + { + return tryReplace(inst->getOperand(0)); + } + else if (isOne(inst->getOperand(1))) + { + return tryReplace(inst->getOperand(0)); + } + } + return false; + } + void processInst(IRInst* inst) { + if (as<IRGlobalValueWithCode>(inst)) + { + if (auto fpModeDecor = inst->findDecoration<IRFloatingModeOverrideDecoration>()) + floatingPointMode = fpModeDecor->getFloatingPointMode(); + } + switch (inst->getOp()) { case kIROp_GetResultError: @@ -432,6 +583,12 @@ struct PeepholeContext : InstPassBase } } break; + case kIROp_Add: + case kIROp_Mul: + case kIROp_Sub: + case kIROp_Div: + changed = tryOptimizeArithmeticInst(inst); + break; default: break; } @@ -443,6 +600,7 @@ struct PeepholeContext : InstPassBase sharedBuilder->init(module); sharedBuilderStorage.deduplicateAndRebuildGlobalNumberingMap(); bool result = false; + for (;;) { changed = false; diff --git a/source/slang/slang-ir-redundancy-removal.cpp b/source/slang/slang-ir-redundancy-removal.cpp index 9bd681115..176142601 100644 --- a/source/slang/slang-ir-redundancy-removal.cpp +++ b/source/slang/slang-ir-redundancy-removal.cpp @@ -109,6 +109,7 @@ bool removeRedundancy(IRModule* module) if (auto func = as<IRFunc>(inst)) { changed |= removeRedundancyInFunc(func); + changed |= eliminateRedundantLoadStore(func); } } return changed; @@ -126,4 +127,95 @@ bool removeRedundancyInFunc(IRGlobalValueWithCode* func) return context.removeRedundancyInBlock(deduplicateCtx, root); } +bool eliminateRedundantLoadStore(IRGlobalValueWithCode* func) +{ + bool changed = false; + for (auto block : func->getBlocks()) + { + for (auto inst = block->getFirstInst(); inst;) + { + auto nextInst = inst->getNextInst(); + if (auto load = as<IRLoad>(inst)) + { + for (auto prev = inst->getPrevInst(); prev; prev = prev->getPrevInst()) + { + if (auto store = as<IRStore>(prev)) + { + if (store->getPtr() == load->getPtr()) + { + // If the load is preceeded by a store without any side-effect insts in-between, remove the load. + auto value = store->getVal(); + load->replaceUsesWith(value); + load->removeAndDeallocate(); + changed = true; + break; + } + } + + if (canInstHaveSideEffectAtAddress(func, prev, load->getPtr())) + { + break; + } + } + } + else if (auto store = as<IRStore>(inst)) + { + // We perform a quick and conservative check: + // A store is redundant if it is followed by another store to the same address in + // the same basic block, and there are no instructions that may use any addresses + // related to this address. + bool hasAddrUse = false; + bool hasOverridingStore = false; + + // Stores to global variables will never get removed. + if (!isChildInstOf(store->getPtr(), func)) + hasAddrUse = true; + + for (auto next = store->getNextInst(); next; next = next->getNextInst()) + { + if (auto nextStore = as<IRStore>(next)) + { + if (nextStore->getPtr() == store->getPtr()) + { + hasOverridingStore = true; + break; + } + } + + // If we see any insts that have reads or modifies the address before seeing + // an overriding store, don't remove the store. + // We can make the test more accurate by collecting all addresses related to + // the target address first, and only bail out if any of the related addresses + // are involved. + switch (next->getOp()) + { + case kIROp_Load: + if (canAddressesPotentiallyAlias(func, next->getOperand(0), store->getPtr())) + { + hasAddrUse = true; + } + break; + default: + if (canInstHaveSideEffectAtAddress(func, next, store->getPtr())) + { + hasAddrUse = true; + } + break; + } + if (hasAddrUse) + break; + } + + if (!hasAddrUse && hasOverridingStore) + { + store->removeAndDeallocate(); + changed = true; + } + } + inst = nextInst; + } + } + return changed; +} + } diff --git a/source/slang/slang-ir-redundancy-removal.h b/source/slang/slang-ir-redundancy-removal.h index 26b265e77..c2df7853e 100644 --- a/source/slang/slang-ir-redundancy-removal.h +++ b/source/slang/slang-ir-redundancy-removal.h @@ -8,4 +8,6 @@ namespace Slang bool removeRedundancy(IRModule* module); bool removeRedundancyInFunc(IRGlobalValueWithCode* func); + + bool eliminateRedundantLoadStore(IRGlobalValueWithCode* func); } diff --git a/source/slang/slang-ir-simplify-for-emit.cpp b/source/slang/slang-ir-simplify-for-emit.cpp new file mode 100644 index 000000000..5e5f61a4a --- /dev/null +++ b/source/slang/slang-ir-simplify-for-emit.cpp @@ -0,0 +1,354 @@ +#include "slang-ir-simplify-for-emit.h" +#include "slang-ir-inst-pass-base.h" +#include "slang-ir-util.h" + +namespace Slang +{ + +struct SimplifyForEmitContext : public InstPassBase +{ + SimplifyForEmitContext(IRModule* inModule) + : InstPassBase(inModule) + {} + + List<IRInst*> followUpWorkList; + HashSet<IRInst*> followUpWorkListSet; + + void addToFollowUpWorkList(IRInst* inst) + { + if (followUpWorkListSet.Add(inst)) + followUpWorkList.add(inst); + } + + void processMakeStruct(IRInst* makeStruct) + { + auto structType = as<IRStructType>(makeStruct->getDataType()); + if (!structType) + return; + for (auto use = makeStruct->firstUse; use;) + { + auto nextUse = use->nextUse; + auto user = use->getUser(); + if (auto store = as<IRStore>(user)) + { + IRBuilder builder(sharedBuilderStorage); + builder.setInsertBefore(user); + UInt i = 0; + for (auto field : structType->getFields()) + { + auto fieldAddr = builder.emitFieldAddress( + builder.getPtrType(field->getFieldType()), + store->getPtr(), + field->getKey()); + builder.emitStore(fieldAddr, makeStruct->getOperand(i)); + addToFollowUpWorkList(makeStruct->getOperand(i)); + i++; + } + store->removeAndDeallocate(); + } + use = nextUse; + } + if (!makeStruct->hasUses()) + makeStruct->removeAndDeallocate(); + } + + void processMakeArray(IRInst* makeArray) + { + auto arrayType = as<IRArrayType>(makeArray->getDataType()); + if (!arrayType) + return; + + for (auto use = makeArray->firstUse; use;) + { + auto nextUse = use->nextUse; + auto user = use->getUser(); + if (auto store = as<IRStore>(user)) + { + IRBuilder builder(sharedBuilderStorage); + builder.setInsertBefore(user); + for (UInt i = 0; i < makeArray->getOperandCount(); i++) + { + auto elementAddr = builder.emitElementAddress( + builder.getPtrType(arrayType->getElementType()), + store->getPtr(), + builder.getIntValue(builder.getIntType(), (IRIntegerValue)i)); + builder.emitStore(elementAddr, makeArray->getOperand(i)); + addToFollowUpWorkList(makeArray->getOperand(i)); + } + store->removeAndDeallocate(); + } + use = nextUse; + } + if (!makeArray->hasUses()) + makeArray->removeAndDeallocate(); + } + + void processMakeArrayFromElement(IRInst* makeArray) + { + auto arrayType = as<IRArrayType>(makeArray->getDataType()); + if (!arrayType) + return; + auto arraySize = as<IRIntLit>(arrayType->getElementCount()); + if (!arraySize) + return; + + for (auto use = makeArray->firstUse; use;) + { + auto nextUse = use->nextUse; + auto user = use->getUser(); + if (auto store = as<IRStore>(user)) + { + IRBuilder builder(sharedBuilderStorage); + builder.setInsertBefore(user); + for (IRIntegerValue i = 0; i < arraySize->getValue(); i++) + { + auto elementAddr = builder.emitElementAddress( + builder.getPtrType(arrayType->getElementType()), + store->getPtr(), + builder.getIntValue(builder.getIntType(), i)); + builder.emitStore(elementAddr, makeArray->getOperand(0)); + addToFollowUpWorkList(makeArray->getOperand(0)); + } + store->removeAndDeallocate(); + } + use = nextUse; + } + if (!makeArray->hasUses()) + makeArray->removeAndDeallocate(); + } + + void processLoadUse(IRGlobalValueWithCode* func, IRLoad* load, IRUse* use) + { + auto user = use->getUser(); + if (user->getParent() != load->getParent()) + return; + for (auto inst = load->getNextInst(); inst; inst = inst->getNextInst()) + { + if (inst == user) + break; + if (canInstHaveSideEffectAtAddress(func, inst, load->getPtr())) + return; + } + + // If we reach here, it is OK to defer the load at use site. + IRBuilder builder(sharedBuilderStorage); + builder.setInsertBefore(user); + auto newLoad = builder.emitLoad(load->getPtr()); + use->set(newLoad); + } + + void processLoad(IRLoad* inst) + { + auto func = getParentFunc(inst); + if (!func) + return; + + for (auto use = inst->firstUse; use;) + { + auto nextUse = use->nextUse; + processLoadUse(func, inst, use); + use = nextUse; + } + + if (!inst->hasUses()) + inst->removeAndDeallocate(); + } + + void processElementExtract(IRInst* inst) + { + // Create a duplicate for each use site. + // This is safe because the result value of this inst should never + // change regardless of where the inst is defined. + // By creating the duplicates right before use sites, we will enable + // the emit logic to always fold these insts. + for (auto use = inst->firstUse; use;) + { + auto nextUse = use->nextUse; + + auto user = use->getUser(); + if (user->getPrevInst() == inst) + { + use = nextUse; + continue; + } + + IRBuilder builder(sharedBuilderStorage); + builder.setInsertBefore(user); + List<IRInst*> args; + for (UInt i = 0; i < inst->getOperandCount(); i++) + args.add(inst->getOperand(i)); + auto newInst = builder.emitIntrinsicInst(inst->getFullType(), inst->getOp(), inst->getOperandCount(), args.getBuffer()); + use->set(newInst); + + use = nextUse; + } + if (!inst->hasUses()) + inst->removeAndDeallocate(); + } + + void processVar(IRInst* var) + { + // Defer var to its first use, if the use is in the same basic block as the var. + HashSet<IRInst*> userInSameBlock; + for (auto use = var->firstUse; use; use = use->nextUse) + if (use->getUser()->getParent() == var->getParent()) + { + userInSameBlock.Add(use->getUser()); + } + IRInst* firstUser = nullptr; + for (auto inst = var->getNextInst(); inst; inst = inst->getNextInst()) + { + if (userInSameBlock.Contains(inst)) + { + firstUser = inst; + break; + } + } + if (!firstUser) + return; + var->insertBefore(firstUser); + } + + void processInst(IRInst* inst) + { + // We inspect each inst and see if the following simplifications + // can be applied: + // 1. If we see `store(addr, MakeArray/Struct)`, we should turn them + // into direct stores into each element/field and remove the need + // to create a temporary for the `MakeArray/Struct` inst. + // 2. If we see `load(addr)`, we duplicate the load right at each + // use site if it can be determined safe to do so. This allows + // emit logic to skip producing a temp var for the loaded result. + switch (inst->getOp()) + { + case kIROp_MakeStruct: + processMakeStruct(inst); + break; + case kIROp_MakeArray: + processMakeArray(inst); + break; + case kIROp_MakeArrayFromElement: + processMakeArrayFromElement(inst); + break; + case kIROp_Load: + processLoad(as<IRLoad>(inst)); + break; + case kIROp_GetElement: + case kIROp_FieldExtract: + processElementExtract(inst); + break; + case kIROp_Var: + processVar(inst); + break; + } + } + + void eliminateCompositeConstruct(IRGlobalValueWithCode* func) + { + followUpWorkList.clear(); + followUpWorkListSet.Clear(); + + for (auto block : func->getBlocks()) + { + for (auto inst = block->getFirstInst(); inst; inst = inst->getNextInst()) + { + switch (inst->getOp()) + { + case kIROp_MakeStruct: + case kIROp_MakeArray: + case kIROp_MakeArrayFromElement: + addToFollowUpWorkList(inst); + break; + } + } + } + for (Index i = 0; i < followUpWorkList.getCount(); i++) + processInst(followUpWorkList[i]); + } + + void deferAndDuplicateLoad(IRGlobalValueWithCode* func) + { + followUpWorkList.clear(); + followUpWorkListSet.Clear(); + + for (auto block : func->getBlocks()) + { + for (auto inst = block->getFirstInst(); inst; inst = inst->getNextInst()) + { + switch (inst->getOp()) + { + case kIROp_Load: + addToFollowUpWorkList(inst); + break; + } + } + } + for (Index i = 0; i < followUpWorkList.getCount(); i++) + processInst(followUpWorkList[i]); + } + + void deferVarDecl(IRGlobalValueWithCode* func) + { + followUpWorkList.clear(); + followUpWorkListSet.Clear(); + + for (auto block : func->getBlocks()) + { + for (auto inst = block->getFirstInst(); inst; inst = inst->getNextInst()) + { + switch (inst->getOp()) + { + case kIROp_Var: + addToFollowUpWorkList(inst); + break; + } + } + } + for (Index i = 0; i < followUpWorkList.getCount(); i++) + processInst(followUpWorkList[i]); + } + + void deferAndDuplicateElementExtract(IRGlobalValueWithCode* func) + { + followUpWorkList.clear(); + followUpWorkListSet.Clear(); + + for (auto block = func->getLastBlock(); block; block = block->getPrevBlock()) + { + for (auto inst = block->getLastChild(); inst; inst = inst->getPrevInst()) + { + switch (inst->getOp()) + { + case kIROp_GetElement: + case kIROp_FieldExtract: + addToFollowUpWorkList(inst); + break; + } + } + } + for (Index i = 0; i < followUpWorkList.getCount(); i++) + processInst(followUpWorkList[i]); + } + + void processFunc(IRGlobalValueWithCode* func) + { + eliminateCompositeConstruct(func); + deferAndDuplicateElementExtract(func); + deferAndDuplicateLoad(func); + deferVarDecl(func); + } + + void processModule() + { + sharedBuilderStorage.init(module); + processInstsOfType<IRFunc>(kIROp_Func, [this](IRFunc* f) { processFunc(f); }); + } +}; + +void simplifyForEmit(IRModule* module) +{ + SimplifyForEmitContext context(module); + context.processModule(); +} + +} diff --git a/source/slang/slang-ir-simplify-for-emit.h b/source/slang/slang-ir-simplify-for-emit.h new file mode 100644 index 000000000..a6cf3bad8 --- /dev/null +++ b/source/slang/slang-ir-simplify-for-emit.h @@ -0,0 +1,9 @@ +// slang-ir-simplify-for-emit.h +#pragma once + +namespace Slang +{ + struct IRModule; + + void simplifyForEmit(IRModule* inModule); +} diff --git a/source/slang/slang-ir-util.cpp b/source/slang/slang-ir-util.cpp index 5cf074484..af6fd8ac4 100644 --- a/source/slang/slang-ir-util.cpp +++ b/source/slang/slang-ir-util.cpp @@ -229,6 +229,217 @@ String dumpIRToString(IRInst* root) return sb.ToString(); } +void copyNameHintDecoration(IRInst* dest, IRInst* src) +{ + auto decor = src->findDecoration<IRNameHintDecoration>(); + if (decor) + { + cloneDecoration(decor, dest); + } +} + +void getTypeNameHint(StringBuilder& sb, IRInst* type) +{ + if (!type) + return; + + switch (type->getOp()) + { + case kIROp_FloatType: + sb << "float"; + break; + case kIROp_HalfType: + sb << "half"; + break; + case kIROp_DoubleType: + sb << "double"; + break; + case kIROp_IntType: + sb << "int"; + break; + case kIROp_Int8Type: + sb << "int8"; + break; + case kIROp_Int16Type: + sb << "int16"; + break; + case kIROp_Int64Type: + sb << "int64"; + break; + case kIROp_IntPtrType: + sb << "intptr"; + break; + case kIROp_UIntType: + sb << "uint"; + break; + case kIROp_UInt8Type: + sb << "uint8"; + break; + case kIROp_UInt16Type: + sb << "uint16"; + break; + case kIROp_UInt64Type: + sb << "uint64"; + break; + case kIROp_UIntPtrType: + sb << "uintptr"; + break; + case kIROp_CharType: + sb << "char"; + break; + case kIROp_StringType: + sb << "string"; + break; + case kIROp_ArrayType: + sb << "array_"; + getTypeNameHint(sb, type->getOperand(0)); + break; + case kIROp_VectorType: + getTypeNameHint(sb, type->getOperand(0)); + getTypeNameHint(sb, as<IRVectorType>(type)->getElementCount()); + break; + case kIROp_MatrixType: + getTypeNameHint(sb, type->getOperand(0)); + getTypeNameHint(sb, as<IRMatrixType>(type)->getRowCount()); + sb << "x"; + getTypeNameHint(sb, as<IRMatrixType>(type)->getColumnCount()); + break; + case kIROp_IntLit: + sb << as<IRIntLit>(type)->getValue(); + break; + default: + if (auto decor = type->findDecoration<IRNameHintDecoration>()) + sb << decor->getName(); + break; + } +} + +static IRInst* _getRootAddr(IRInst* addr) +{ + for (;;) + { + switch (addr->getOp()) + { + case kIROp_GetElementPtr: + case kIROp_FieldAddress: + addr = addr->getOperand(0); + continue; + default: + break; + } + break; + } + return addr; +} + +// A simple and conservative address aliasing check. +bool canAddressesPotentiallyAlias(IRGlobalValueWithCode* func, IRInst* addr1, IRInst* addr2) +{ + if (addr1 == addr2) + return true; + + // Two variables can never alias. + addr1 = _getRootAddr(addr1); + addr2 = _getRootAddr(addr2); + + // Global addresses can alias with anything. + if (!isChildInstOf(addr1, func)) + return true; + + if (!isChildInstOf(addr2, func)) + return true; + + if (addr1->getOp() == kIROp_Var && addr2->getOp() == kIROp_Var + && addr1 != addr2) + return false; + + // A param and a var can never alias. + if (addr1->getOp() == kIROp_Param && addr1->getParent() == func->getFirstBlock() && + addr2->getOp() == kIROp_Var || + addr1->getOp() == kIROp_Var && addr2->getOp() == kIROp_Param && + addr2->getParent() == func->getFirstBlock()) + return false; + return true; +} + +bool isPtrLikeOrHandleType(IRInst* type) +{ + switch (type->getOp()) + { + case kIROp_ComPtrType: + case kIROp_RawPointerType: + case kIROp_RTTIPointerType: + case kIROp_PseudoPtrType: + case kIROp_OutType: + case kIROp_InOutType: + case kIROp_PtrType: + case kIROp_RefType: + return true; + } + return false; +} + +bool canInstHaveSideEffectAtAddress(IRGlobalValueWithCode* func, IRInst* inst, IRInst* addr) +{ + switch (inst->getOp()) + { + case kIROp_Store: + // If the target of the store inst may overlap addr, return true. + if (canAddressesPotentiallyAlias(func, as<IRStore>(inst)->getPtr(), addr)) + return true; + break; + case kIROp_Call: + { + auto call = as<IRCall>(inst); + + // If addr is a global variable, calling a function may change its value. + // So we need to return true here to be conservative. + if (!isChildInstOf(_getRootAddr(addr), func)) + { + auto callee = call->getCallee(); + if (callee && + callee->findDecoration<IRReadNoneDecoration>() && + callee->findDecoration<IRNoSideEffectDecoration>()) + { + // An exception is if the callee is side-effect free and is not reading from + // memory. + } + else + { + return true; + } + } + + // If any pointer typed argument of the call inst may overlap addr, return true. + for (UInt i = 0; i < call->getArgCount(); i++) + { + if (isPtrLikeOrHandleType(call->getArg(i)->getDataType())) + { + if (canAddressesPotentiallyAlias(func, call->getArg(i), addr)) + return true; + } + } + } + break; + case kIROp_CastPtrToInt: + case kIROp_Reinterpret: + case kIROp_BitCast: + { + // If we are trying to cast an address to something else, return true. + if (isPtrLikeOrHandleType(inst->getOperand(0)->getDataType()) && + canAddressesPotentiallyAlias(func, inst->getOperand(0), addr)) + return true; + } + break; + default: + // Default behavior is that any insts that have side effect may affect `addr`. + if (inst->mightHaveSideEffects()) + return true; + break; + } + return false; +} + bool isPureFunctionalCall(IRCall* call) { auto callee = getResolvedInstForDecorations(call->getCallee()); diff --git a/source/slang/slang-ir-util.h b/source/slang/slang-ir-util.h index 26ad4bc68..c067bde44 100644 --- a/source/slang/slang-ir-util.h +++ b/source/slang/slang-ir-util.h @@ -153,11 +153,20 @@ inline IRInst* unwrapAttributedType(IRInst* type) return type; } +void getTypeNameHint(StringBuilder& sb, IRInst* type); +void copyNameHintDecoration(IRInst* dest, IRInst* src); + +bool canAddressesPotentiallyAlias(IRGlobalValueWithCode* func, IRInst* addr1, IRInst* addr2); + String dumpIRToString(IRInst* root); // Returns whether a call insts can be treated as a pure functional inst // (no writes to memory, no side effects). bool isPureFunctionalCall(IRCall* callInst); + +bool isPtrLikeOrHandleType(IRInst* type); + +bool canInstHaveSideEffectAtAddress(IRGlobalValueWithCode* func, IRInst* inst, IRInst* addr); } #endif diff --git a/source/slang/slang-ir.cpp b/source/slang/slang-ir.cpp index 558574bf6..1b16bfe1f 100644 --- a/source/slang/slang-ir.cpp +++ b/source/slang/slang-ir.cpp @@ -4604,6 +4604,14 @@ namespace Slang return inst; } + IRInst* IRBuilder::addFloatingModeOverrideDecoration(IRInst* dest, FloatingPointMode mode) + { + return addDecoration( + dest, + kIROp_FloatingPointModeOverrideDecoration, + getIntValue(getIntType(), (IRIntegerValue)mode)); + } + IRInst* IRBuilder::emitSwizzle( IRType* type, IRInst* base, @@ -6418,6 +6426,20 @@ namespace Slang return false; } + bool isIntegralScalarOrCompositeType(IRType* t) + { + if (!t) + return false; + switch (t->getOp()) + { + case kIROp_VectorType: + case kIROp_MatrixType: + return isIntegralType((IRType*)t->getOperand(0)); + default: + return isIntegralType(t); + } + } + void findAllInstsBreadthFirst(IRInst* inst, List<IRInst*>& outInsts) { Index index = outInsts.getCount(); @@ -6577,6 +6599,8 @@ namespace Slang void IRInst::insertBefore(IRInst* other) { SLANG_ASSERT(other); + if (other->getPrevInst() == this) + return; _insertAt(other->getPrevInst(), other, other->getParent()); } diff --git a/source/slang/slang-ir.h b/source/slang/slang-ir.h index e22e41f0c..41b140972 100644 --- a/source/slang/slang-ir.h +++ b/source/slang/slang-ir.h @@ -869,6 +869,8 @@ bool isTypeEqual(IRType* a, IRType* b); // True if this is an integral IRBasicType, not including Char or Ptr types bool isIntegralType(IRType* t); +bool isIntegralScalarOrCompositeType(IRType* t); + void findAllInstsBreadthFirst(IRInst* inst, List<IRInst*>& outInsts); // Constant Instructions @@ -943,6 +945,13 @@ struct IRIntLit : IRConstant IR_LEAF_ISA(IntLit); }; +struct IRFloatLit : IRConstant +{ + IRFloatingPointValue getValue() { return value.floatVal; } + + IR_LEAF_ISA(FloatLit); +}; + struct IRBoolLit : IRConstant { bool getValue() { return value.intVal != 0; } diff --git a/source/slang/slang-lower-to-ir.cpp b/source/slang/slang-lower-to-ir.cpp index 149f5f6b9..8377246fb 100644 --- a/source/slang/slang-lower-to-ir.cpp +++ b/source/slang/slang-lower-to-ir.cpp @@ -3304,6 +3304,15 @@ struct ExprLoweringVisitorBase : ExprVisitor<Derived, LoweredValInfo> } } + LoweredValInfo visitMakeRefExpr(MakeRefExpr* expr) + { + auto loweredBase = lowerLValueExpr(context, expr->base); + + SLANG_ASSERT(loweredBase.flavor == LoweredValInfo::Flavor::Ptr); + loweredBase.flavor = LoweredValInfo::Flavor::Simple; + return loweredBase; + } + LoweredValInfo visitParenExpr(ParenExpr* expr) { return lowerSubExpr(expr->base); @@ -4234,11 +4243,11 @@ struct ExprLoweringVisitorBase : ExprVisitor<Derived, LoweredValInfo> switch (baseVal.flavor) { case LoweredValInfo::Flavor::Simple: - return LoweredValInfo::simple( - builder->emitElementExtract( - type, - getSimpleVal(context, baseVal), - indexVal)); + return LoweredValInfo::simple( + builder->emitElementExtract( + type, + getSimpleVal(context, baseVal), + indexVal)); case LoweredValInfo::Flavor::Ptr: return LoweredValInfo::ptr( @@ -4416,7 +4425,11 @@ struct ExprLoweringVisitorBase : ExprVisitor<Derived, LoweredValInfo> LoweredValInfo visitOpenRefExpr(OpenRefExpr* expr) { - return lowerLValueExpr(context, expr->innerExpr); + auto info = lowerRValueExpr(context, expr->innerExpr); + SLANG_RELEASE_ASSERT(as<IRPtrTypeBase>(info.val->getFullType())); + SLANG_RELEASE_ASSERT(info.flavor == LoweredValInfo::Flavor::Simple); + info.flavor = LoweredValInfo::Flavor::Ptr; + return info; } }; @@ -4596,10 +4609,6 @@ LoweredValInfo lowerLValueExpr( LValueExprLoweringVisitor visitor; visitor.context = context; auto info = visitor.dispatch(expr); - if (as<RefType>(expr->type)) - { - info.flavor = LoweredValInfo::Flavor::Ptr; - } return info; } @@ -4612,10 +4621,6 @@ LoweredValInfo lowerRValueExpr( RValueExprLoweringVisitor visitor; visitor.context = context; auto info = visitor.dispatch(expr); - if (as<RefType>(expr->type)) - { - info.val = context->irBuilder->emitLoad(info.val); - } return info; } diff --git a/tests/compute/unbounded-array-of-array-syntax.slang.glsl b/tests/compute/unbounded-array-of-array-syntax.slang.glsl index 6ee5d1c6b..b71b0cd7c 100644 --- a/tests/compute/unbounded-array-of-array-syntax.slang.glsl +++ b/tests/compute/unbounded-array-of-array-syntax.slang.glsl @@ -1,9 +1,9 @@ //TEST_IGNORE_FILE: #version 450 +#extension GL_EXT_nonuniform_qualifier : require layout(row_major) uniform; layout(row_major) buffer; -#extension GL_EXT_nonuniform_qualifier : require layout(std430, binding = 1) buffer _S1 { int _data[]; @@ -18,21 +18,21 @@ void main() int index_0 = int(gl_GlobalInvocationID.x); int innerIndex_0 = index_0 & 3; + int _S3 = nonuniformEXT(index_0 >> 2); uint bufferCount_0; uint bufferStride_0; - (bufferCount_0) = (g_aoa_0[nonuniformEXT(index_0 >> 2)])._data.length(); - (bufferStride_0) = 0; + (bufferCount_0) = (g_aoa_0[_S3])._data.length(); (bufferStride_0) = 0; int innerIndex_1; if(uint(innerIndex_0) >= bufferCount_0) { - innerIndex_1 = int(bufferCount_0 - uint(1)); + innerIndex_1 = int(bufferCount_0 - 1U); } else { innerIndex_1 = innerIndex_0; } - uint _S3 = uint(innerIndex_1); - ((outputBuffer_0)._data[(uint(index_0))]) = ((g_aoa_0[nonuniformEXT(index_0 >> 2)])._data[(_S3)]); + uint _S4 = uint(innerIndex_1); + ((outputBuffer_0)._data[(uint(index_0))]) = ((g_aoa_0[_S3])._data[(_S4)]); return; } diff --git a/tests/cross-compile/array-of-buffers.slang.glsl b/tests/cross-compile/array-of-buffers.slang.glsl index 3dfe31d8d..1f436fad0 100644 --- a/tests/cross-compile/array-of-buffers.slang.glsl +++ b/tests/cross-compile/array-of-buffers.slang.glsl @@ -1,5 +1,7 @@ //TEST_IGNORE_FILE: #version 450 +layout(row_major) uniform; +layout(row_major) buffer; struct SLANG_ParameterGroup_C_0 { @@ -23,19 +25,15 @@ layout(std140) uniform _S2 S_0 _data; } cb_0[3]; - -layout(std430, binding = 2) -readonly buffer _S3 { +layout(std430, binding = 2) readonly buffer _S3 { S_0 _data[]; } sb1_0[4]; -layout(std430, binding = 3) -buffer _S4 { +layout(std430, binding = 3) buffer _S4 { vec4 _data[]; } sb2_0[5]; -layout(std430, binding = 4) -readonly buffer _S5 +layout(std430, binding = 4) readonly buffer _S5 { uint _data[]; } bb_0[6]; @@ -45,13 +43,12 @@ out vec4 _S6; void main() { - vec4 _S7 = cb_0[C_0._data.index_0]._data.f_0; + S_0 _S7 = ((sb1_0[C_0._data.index_0])._data[(C_0._data.index_0)]); + vec4 _S8 = cb_0[C_0._data.index_0]._data.f_0 + _S7.f_0; + vec4 _S9 = _S8 + ((sb2_0[C_0._data.index_0])._data[(C_0._data.index_0)]); + uint _S10 = ((bb_0[C_0._data.index_0])._data[(int(C_0._data.index_0 * 4U))/4]); - S_0 _S8 = sb1_0[C_0._data.index_0]._data[C_0._data.index_0]; + _S6 = _S9 + vec4(float(_S10)); - vec4 _S9 = _S7 + _S8.f_0; - vec4 _S10 = _S9 + sb2_0[C_0._data.index_0]._data[C_0._data.index_0]; - uint _S11 = bb_0[C_0._data.index_0]._data[int(C_0._data.index_0 * uint(4))/4]; - _S6 = _S10 + vec4(_S11); return; } diff --git a/tests/cross-compile/array-of-buffers.slang.hlsl b/tests/cross-compile/array-of-buffers.slang.hlsl index 37f4639a7..501b9c6db 100644 --- a/tests/cross-compile/array-of-buffers.slang.hlsl +++ b/tests/cross-compile/array-of-buffers.slang.hlsl @@ -1,5 +1,11 @@ //TEST_IGNORE_FILE: +#pragma pack_matrix(column_major) +#ifdef SLANG_HLSL_ENABLE_NVAPI +#include "nvHLSLExtns.h" +#endif +#pragma warning(disable: 3557) + struct SLANG_ParameterGroup_C_0 { uint index_0; @@ -15,21 +21,18 @@ struct S_0 float4 f_0; }; -ConstantBuffer<S_0> cb_0 [3] : register(b1); -StructuredBuffer<S_0> sb1_0[4] : register(t0); -RWStructuredBuffer<float4> sb2_0[5] : register(u0); -ByteAddressBuffer bb_0[6] : register(t4); +ConstantBuffer<S_0 > cb_0[int(3)] : register(b1); +StructuredBuffer<S_0 > sb1_0[int(4)] : register(t0); +RWStructuredBuffer<float4 > sb2_0[int(5)] : register(u0); +ByteAddressBuffer bb_0[int(6)] : register(t4); float4 main() : SV_TARGET { - float4 _S1 = cb_0[C_0.index_0].f_0; - - S_0 _S2 = sb1_0[C_0.index_0][C_0.index_0]; + S_0 _S1 = sb1_0[C_0.index_0][C_0.index_0]; - float4 _S3 = _S1 + _S2.f_0; - float4 _S4 = _S3 + sb2_0[C_0.index_0][C_0.index_0]; - uint _S5 = bb_0[C_0.index_0].Load( - (int) (C_0.index_0 * (uint) 4)); + float4 _S2 = cb_0[C_0.index_0].f_0 + _S1.f_0; + float4 _S3 = _S2 + sb2_0[C_0.index_0][C_0.index_0]; + uint _S4 = bb_0[C_0.index_0].Load(int(C_0.index_0 * 4U)); - return _S4 + (float4) _S5; + return _S3 + (float4)float(_S4); } diff --git a/tests/cross-compile/dual-source-blending.slang.glsl b/tests/cross-compile/dual-source-blending.slang.glsl index f10eb77a0..aa550b451 100644 --- a/tests/cross-compile/dual-source-blending.slang.glsl +++ b/tests/cross-compile/dual-source-blending.slang.glsl @@ -21,16 +21,16 @@ struct FragmentOutput_0 void main() { + const vec4 _S4 = vec4(0.0, 0.0, 0.0, 0.0); FragmentOutput_0 f_0; - FragmentOutput_0 _S4 = { vec4(0.0, 0.0, 0.0, 0.0), vec4(0.0, 0.0, 0.0, 0.0) }; - f_0 = _S4; + f_0.a_0 = _S4; + f_0.b_0 = _S4; f_0.a_0 = _S3; f_0.b_0 = _S3; - FragmentOutput_0 _S5 = f_0; - _S1 = _S5.a_0; + _S1 = f_0.a_0; _S2 = _S5.b_0; return; diff --git a/tests/cross-compile/geometry-shader.slang.glsl b/tests/cross-compile/geometry-shader.slang.glsl index 1664e8468..38dbd72ba 100644 --- a/tests/cross-compile/geometry-shader.slang.glsl +++ b/tests/cross-compile/geometry-shader.slang.glsl @@ -64,8 +64,8 @@ void main() CoarseVertex_0 _S10[3] = { _S7, _S8, _S9 }; - int ii_0; - ii_0 = 0; + int ii_0 = 0; + for(;;) { if(ii_0 < 3) @@ -75,17 +75,14 @@ void main() break; } - CoarseVertex_0 coarseVertex_0 = _S10[ii_0]; - RasterVertex_0 rasterVertex_0; - rasterVertex_0.position_0 = coarseVertex_0.position_1; - rasterVertex_0.color_0 = coarseVertex_0.color_1; - rasterVertex_0.id_0 = coarseVertex_0.id_1 + _S6; - + rasterVertex_0.position_0 = _S10[ii_0].position_1; + rasterVertex_0.color_0 = _S10[ii_0].color_1; + rasterVertex_0.id_0 = _S10[ii_0].id_1 + _S6; RasterVertex_0 _S11 = rasterVertex_0; + _S4 = rasterVertex_0.position_0; + _S5 = _S11.color_0; - output_position = _S11.position_0; - output_color = _S11.color_0; gl_Layer = int(_S11.id_0); EmitVertex(); diff --git a/tests/cross-compile/unknown-image-format.slang.glsl b/tests/cross-compile/unknown-image-format.slang.glsl index 329405ab6..5ccc30767 100644 --- a/tests/cross-compile/unknown-image-format.slang.glsl +++ b/tests/cross-compile/unknown-image-format.slang.glsl @@ -3,6 +3,8 @@ #version 450 #extension GL_EXT_shader_image_load_formatted : require +layout(row_major) uniform; +layout(row_major) buffer; struct SLANG_ParameterGroup_C_0 { @@ -41,25 +43,24 @@ out vec4 _S2; void main() { - const vec4 result_0 = vec4(0); float _S3 = (imageLoad((gNoFormat_0), ivec2((C_0._data.index_0))).x); - vec4 result_1 = result_0 + _S3; + vec4 _S4 = vec4(_S3); - float _S4 = (imageLoad((gExplicitFormat_0), ivec2((C_0._data.index_0))).x); - vec4 result_2 = result_1 + _S4; + float _S5 = (imageLoad((gExplicitFormat_0), ivec2((C_0._data.index_0))).x); + vec4 result_0 = _S4 + _S5; - vec4 _S5 = (imageLoad((gBlock_noFormat_0), ivec2((C_0._data.index_0)))); - vec4 result_3 = result_2 + _S5; + vec4 _S6 = (imageLoad((gBlock_noFormat_0), ivec2((C_0._data.index_0)))); + vec4 result_1 = result_0 + _S6; - vec4 _S6 = (imageLoad((gBlock_explicitFormat_0), ivec2((C_0._data.index_0)))); - vec4 result_4 = result_3 + _S6; + vec4 _S7 = (imageLoad((gBlock_explicitFormat_0), ivec2((C_0._data.index_0)))); + vec4 result_2 = result_1 + _S7; - vec4 _S7 = (imageLoad((entryPointParams_noFormat_0), ivec2((C_0._data.index_0)))); - vec4 result_5 = result_4 + _S7; + vec4 _S8 = (imageLoad((entryPointParams_noFormat_0), ivec2((C_0._data.index_0)))); + vec4 result_3 = result_2 + _S8; - vec4 _S8 = (imageLoad((entryPointParams_explicitFormat_0), ivec2((C_0._data.index_0)))); - _S2 = result_5 + _S8; + vec4 _S9 = (imageLoad((entryPointParams_explicitFormat_0), ivec2((C_0._data.index_0)))); + _S2 = result_3 + _S9; return; } diff --git a/tests/cross-compile/vector-comparison.slang.glsl b/tests/cross-compile/vector-comparison.slang.glsl index 77578a368..2497055a0 100644 --- a/tests/cross-compile/vector-comparison.slang.glsl +++ b/tests/cross-compile/vector-comparison.slang.glsl @@ -19,8 +19,6 @@ out vec4 _S2; void main() { - vec4 v0_0 = params_0._data.a_0; - vec4 v1_0 = params_0._data.b_0; - _S2 = mix(vec4(3.00000000000000000000), vec4(2.00000000000000000000), equal(v0_0,v1_0)) + mix(vec4(3.00000000000000000000), vec4(2.00000000000000000000), lessThan(v0_0,v1_0)) + mix(vec4(3.00000000000000000000), vec4(2.00000000000000000000), greaterThan(v0_0,v1_0)) + mix(vec4(3.00000000000000000000), vec4(2.00000000000000000000), lessThanEqual(v0_0,v1_0)) + mix(vec4(3.00000000000000000000), vec4(2.00000000000000000000), greaterThanEqual(v0_0,v1_0)) + mix(vec4(3.00000000000000000000), vec4(2.00000000000000000000), notEqual(v0_0,v1_0)); + _S2 = mix(vec4(3.0), vec4(2.0), (equal(params_0._data.a_0,params_0._data.b_0))) + mix(vec4(3.0), vec4(2.0), (lessThan(params_0._data.a_0,params_0._data.b_0))) + mix(vec4(3.0), vec4(2.0), (greaterThan(params_0._data.a_0,params_0._data.b_0))) + mix(vec4(3.0), vec4(2.0), (lessThanEqual(params_0._data.a_0,params_0._data.b_0))) + mix(vec4(3.0), vec4(2.0), (greaterThanEqual(params_0._data.a_0,params_0._data.b_0))) + mix(vec4(3.0), vec4(2.0), (notEqual(params_0._data.a_0,params_0._data.b_0))); return; } diff --git a/tests/experimental/liveness/liveness-3.slang.expected b/tests/experimental/liveness/liveness-3.slang.expected index dac9ff1bd..4dff6b37a 100644 --- a/tests/experimental/liveness/liveness-3.slang.expected +++ b/tests/experimental/liveness/liveness-3.slang.expected @@ -28,15 +28,15 @@ int calcThing_0(int offset_0) { int another_0[2]; livenessStart_0(another_0, 0); - const int _S1[2] = { 1, 2 }; - another_0 = _S1; + another_0[0] = 1; + another_0[1] = 2; int k_0; - int _S2; - int total_0; livenessStart_1(k_0, 0); k_0 = 0; - livenessStart_1(_S2, 0); - _S2 = offset_0; + int _S1; + livenessStart_1(_S1, 0); + _S1 = offset_0; + int total_0; livenessStart_1(total_0, 0); total_0 = 0; for(;;) @@ -50,15 +50,15 @@ int calcThing_0(int offset_0) } int idx_0[3]; livenessStart_2(idx_0, 0); - const int _S3[3] = { 0, 0, 0 }; - idx_0 = _S3; + idx_0[0] = 0; + idx_0[1] = 0; + idx_0[2] = 0; int i_0; - int _S4; - int _S5 = _S2; livenessStart_1(i_0, 0); i_0 = 0; - livenessStart_1(_S4, 0); - _S4 = _S5; + int _S2; + livenessStart_1(_S2, 0); + _S2 = _S1; for(;;) { if(i_0 < 17) @@ -70,74 +70,74 @@ int calcThing_0(int offset_0) } int modRange_0 = i_0 % 3; another_0[i_0 & 1] = another_0[i_0 & 1] + modRange_0; - int _S6 = i_0 % 3; - int _S7; - if(_S6 != 0) + int _S3 = i_0 % 3; + int _S4; + if(_S3 != 0) { - int _S8 = _S4; - livenessEnd_0(_S4, 0); - int _S9 = _S8 + 1; - livenessStart_1(_S7, 0); - _S7 = _S9; + int _S5 = _S2; + livenessEnd_0(_S2, 0); + int _S6 = _S5 + 1; + livenessStart_1(_S4, 0); + _S4 = _S6; } else { - int _S10 = _S4; - livenessEnd_0(_S4, 0); - livenessStart_1(_S7, 0); - _S7 = _S10; + int _S7 = _S2; + livenessEnd_0(_S2, 0); + livenessStart_1(_S4, 0); + _S4 = _S7; } - idx_0[modRange_0] = idx_0[modRange_0] + (_S7 + i_0); + idx_0[modRange_0] = idx_0[modRange_0] + (_S4 + i_0); i_0 = i_0 + 1; - livenessStart_1(_S4, 0); - int _S11 = _S7; - livenessEnd_0(_S7, 0); - _S4 = _S11; + livenessStart_1(_S2, 0); + int _S8 = _S4; + livenessEnd_0(_S4, 0); + _S2 = _S8; } livenessEnd_0(i_0, 0); - livenessEnd_0(_S2, 0); - int _S12 = (k_0 + 7) % 5; - if(_S12 == 4) + livenessEnd_0(_S1, 0); + int _S9 = (k_0 + 7) % 5; + if(_S9 == 4) { - livenessEnd_0(_S4, 0); + livenessEnd_0(_S2, 0); livenessEnd_1(idx_0, 0); livenessEnd_0(k_0, 0); livenessEnd_2(another_0, 0); return total_0; } - int _S13 = idx_0[0] + idx_0[1]; - int _S14 = idx_0[2]; + int _S10 = idx_0[0] + idx_0[1]; + int _S11 = idx_0[2]; livenessEnd_1(idx_0, 0); - int _S15 = _S13 + _S14; - int _S16 = total_0; + int _S12 = _S10 + _S11; + int _S13 = total_0; livenessEnd_0(total_0, 0); - int total_1 = _S16 + _S15; + int total_1 = _S13 + _S12; k_0 = k_0 + 1; - livenessStart_1(_S2, 0); - int _S17 = _S4; - livenessEnd_0(_S4, 0); - _S2 = _S17; + livenessStart_1(_S1, 0); + int _S14 = _S2; + livenessEnd_0(_S2, 0); + _S1 = _S14; livenessStart_1(total_0, 0); total_0 = total_1; } - livenessEnd_0(_S2, 0); + livenessEnd_0(_S1, 0); livenessEnd_0(k_0, 0); livenessEnd_2(another_0, 0); - int _S18 = total_0; + int _S15 = total_0; livenessEnd_0(total_0, 0); - return - _S18; + return - _S15; } -layout(std430, binding = 0) buffer _S19 { +layout(std430, binding = 0) buffer _S16 { int _data[]; } outputBuffer_0; layout(local_size_x = 4, local_size_y = 1, local_size_z = 1) in; void main() { int index_0 = int(gl_GlobalInvocationID.x); - uint _S20 = uint(index_0); - int _S21 = calcThing_0(index_0); - ((outputBuffer_0)._data[(_S20)]) = _S21; + uint _S17 = uint(index_0); + int _S18 = calcThing_0(index_0); + ((outputBuffer_0)._data[(_S17)]) = _S18; return; } diff --git a/tests/experimental/liveness/liveness-4.slang.expected b/tests/experimental/liveness/liveness-4.slang.expected index 52c6ebb32..cd97f8057 100644 --- a/tests/experimental/liveness/liveness-4.slang.expected +++ b/tests/experimental/liveness/liveness-4.slang.expected @@ -22,8 +22,8 @@ int calcThing_0(int offset_0) { int another_0[2]; livenessStart_0(another_0, 0); - const int _S1[2] = { 1, 2 }; - another_0 = _S1; + another_0[0] = 1; + another_0[1] = 2; int k_0; livenessStart_1(k_0, 0); k_0 = 0; @@ -52,8 +52,8 @@ int calcThing_0(int offset_0) i_0 = i_0 + 1; } livenessEnd_0(i_0, 0); - int _S2 = (k_0 + 7) % 5; - if(_S2 == 4) + int _S1 = (k_0 + 7) % 5; + if(_S1 == 4) { livenessEnd_0(k_0, 0); livenessEnd_1(another_0, 0); @@ -66,16 +66,16 @@ int calcThing_0(int offset_0) return -2; } -layout(std430, binding = 0) buffer _S3 { +layout(std430, binding = 0) buffer _S2 { int _data[]; } outputBuffer_0; layout(local_size_x = 4, local_size_y = 1, local_size_z = 1) in; void main() { int index_0 = int(gl_GlobalInvocationID.x); - uint _S4 = uint(index_0); - int _S5 = calcThing_0(index_0); - ((outputBuffer_0)._data[(_S4)]) = _S5; + uint _S3 = uint(index_0); + int _S4 = calcThing_0(index_0); + ((outputBuffer_0)._data[(_S3)]) = _S4; return; } diff --git a/tests/experimental/liveness/liveness-5.slang.expected b/tests/experimental/liveness/liveness-5.slang.expected index a8a9707d7..3693d3fde 100644 --- a/tests/experimental/liveness/liveness-5.slang.expected +++ b/tests/experimental/liveness/liveness-5.slang.expected @@ -22,12 +22,12 @@ int calcThing_0(int offset_0) { int another_0[2]; livenessStart_0(another_0, 0); - const int _S1[2] = { 1, 2 }; - another_0 = _S1; + another_0[0] = 1; + another_0[1] = 2; int k_0; - int total_0; livenessStart_1(k_0, 0); k_0 = 0; + int total_0; livenessStart_1(total_0, 0); total_0 = 0; for(;;) @@ -55,12 +55,11 @@ int calcThing_0(int offset_0) i_0 = i_0 + 1; } livenessEnd_0(i_0, 0); - int _S2 = another_0[k_0 & 1]; - int _S3 = total_0; + int _S1 = total_0; livenessEnd_0(total_0, 0); - int total_1 = _S3 + _S2; - int _S4 = (k_0 + 7) % 5; - if(_S4 == 4) + int total_1 = _S1 + another_0[k_0 & 1]; + int _S2 = (k_0 + 7) % 5; + if(_S2 == 4) { livenessEnd_0(k_0, 0); livenessEnd_1(another_0, 0); @@ -82,16 +81,16 @@ int calcThing_0(int offset_0) return total_0; } -layout(std430, binding = 0) buffer _S5 { +layout(std430, binding = 0) buffer _S3 { int _data[]; } outputBuffer_0; layout(local_size_x = 4, local_size_y = 1, local_size_z = 1) in; void main() { int index_0 = int(gl_GlobalInvocationID.x); - uint _S6 = uint(index_0); - int _S7 = calcThing_0(index_0); - ((outputBuffer_0)._data[(_S6)]) = _S7; + uint _S4 = uint(index_0); + int _S5 = calcThing_0(index_0); + ((outputBuffer_0)._data[(_S4)]) = _S5; return; } diff --git a/tests/experimental/liveness/liveness-6.slang.expected b/tests/experimental/liveness/liveness-6.slang.expected index 402e19886..9c3bae815 100644 --- a/tests/experimental/liveness/liveness-6.slang.expected +++ b/tests/experimental/liveness/liveness-6.slang.expected @@ -22,12 +22,12 @@ int calcThing_0(int offset_0) { int another_0[2]; livenessStart_0(another_0, 0); - const int _S1[2] = { 1, 2 }; - another_0 = _S1; + another_0[0] = 1; + another_0[1] = 2; int k_0; - int total_0; livenessStart_1(k_0, 0); k_0 = 0; + int total_0; livenessStart_1(total_0, 0); total_0 = 0; for(;;) @@ -41,8 +41,8 @@ int calcThing_0(int offset_0) } int arr_0[2]; livenessStart_0(arr_0, 0); - const int _S2[2] = { 2, 3 }; - arr_0 = _S2; + arr_0[0] = 2; + arr_0[1] = 3; int i_0; livenessStart_1(i_0, 0); i_0 = 0; @@ -60,16 +60,15 @@ int calcThing_0(int offset_0) i_0 = i_0 + 1; } livenessEnd_0(i_0, 0); - int _S3 = k_0 & 1; - int _S4 = another_0[_S3]; - int _S5 = total_0; + int _S1 = k_0 & 1; + int _S2 = total_0; livenessEnd_0(total_0, 0); - int total_1 = _S5 + _S4; - int _S6 = arr_0[_S3]; + int total_1 = _S2 + another_0[_S1]; + int _S3 = arr_0[_S1]; livenessEnd_1(arr_0, 0); - int total_2 = total_1 + _S6; - int _S7 = (k_0 + 7) % 5; - if(_S7 == 4) + int total_2 = total_1 + _S3; + int _S4 = (k_0 + 7) % 5; + if(_S4 == 4) { livenessEnd_0(k_0, 0); livenessEnd_1(another_0, 0); @@ -91,16 +90,16 @@ int calcThing_0(int offset_0) return total_0; } -layout(std430, binding = 0) buffer _S8 { +layout(std430, binding = 0) buffer _S5 { int _data[]; } outputBuffer_0; layout(local_size_x = 4, local_size_y = 1, local_size_z = 1) in; void main() { int index_0 = int(gl_GlobalInvocationID.x); - uint _S9 = uint(index_0); - int _S10 = calcThing_0(index_0); - ((outputBuffer_0)._data[(_S9)]) = _S10; + uint _S6 = uint(index_0); + int _S7 = calcThing_0(index_0); + ((outputBuffer_0)._data[(_S6)]) = _S7; return; } diff --git a/tests/experimental/liveness/liveness.slang.expected b/tests/experimental/liveness/liveness.slang.expected index e50ecac5a..4a81b8855 100644 --- a/tests/experimental/liveness/liveness.slang.expected +++ b/tests/experimental/liveness/liveness.slang.expected @@ -22,9 +22,9 @@ int someSlowFunc_0(int a_0) { uint _S1 = uint(a_0); uint v_0; - int i_0; livenessStart_0(v_0, 0); v_0 = _S1; + int i_0; livenessStart_1(i_0, 0); i_0 = 0; for(;;) @@ -91,9 +91,9 @@ void main() { int index_0 = int(gl_GlobalInvocationID.x); int i_2; - int res_0; livenessStart_1(i_2, 0); i_2 = 0; + int res_0; livenessStart_1(res_0, 0); res_0 = index_0; for(;;) @@ -113,30 +113,33 @@ void main() SomeStruct_0 _S8 = makeSomeStruct_0(); t_0 = _S8; const int _S9[100] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; - SomeStruct_0 u_0 = { 0, 0, _S9 }; - SomeStruct_0 u_1; + SomeStruct_0 u_0; if((v_1 & 256) != 0) { s_3.x_0 = ((anotherBuffer_0)._data[(uint(v_1 & 3))]); t_0.x_0 = ((anotherBuffer_0)._data[(uint(v_1 & 3))]); - livenessStart_2(u_1, 0); - u_1 = u_0; + livenessStart_2(u_0, 0); + u_0.a_1 = 0; + u_0.x_0 = 0; + u_0.c_0 = _S9; } else { SomeStruct_0 x_1; livenessStart_2(x_1, 0); - x_1 = u_0; + x_1.a_1 = 0; + x_1.x_0 = 0; + x_1.c_0 = _S9; x_1.x_0 = ((anotherBuffer_0)._data[(uint(v_1 & 3))]) + 1; SomeStruct_0 _S10 = x_1; livenessEnd_2(x_1, 0); - livenessStart_2(u_1, 0); - u_1 = _S10; + livenessStart_2(u_0, 0); + u_0 = _S10; } s_3.c_0[index_0 & 7] = s_3.c_0[index_0 & 7] + 1; int _S11 = s_3.x_0 + t_0.x_0; - SomeStruct_0 _S12 = u_1; - livenessEnd_2(u_1, 0); + SomeStruct_0 _S12 = u_0; + livenessEnd_2(u_0, 0); int _S13 = _S11 + _S12.x_0; int _S14 = doThing_0(t_0); int _S15 = _S13 + _S14; diff --git a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-assign.slang.1.expected b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-assign.slang.1.expected index 22affc22e..d921747af 100644 --- a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-assign.slang.1.expected +++ b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-assign.slang.1.expected @@ -25,19 +25,17 @@ void main() uvec3 _S3 = ((gl_LaunchSizeEXT)); int idx_0 = launchID_0.x; RayDesc_0 ray_0; - ray_0.Origin_0 = vec3(float(idx_0), 0.00000000000000000000, 0.00000000000000000000); + ray_0.Origin_0 = vec3(float(idx_0), 0.0, 0.0); ray_0.TMin_0 = 0.00999999977648258209; - ray_0.Direction_0 = vec3(0.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000); - ray_0.TMax_0 = 10000.00000000000000000000; - RayDesc_0 _S4 = ray_0; + ray_0.Direction_0 = vec3(0.0, 1.0, 0.0); + ray_0.TMax_0 = 10000.0; hitObjectNV hitObj_0; - hitObjectRecordMissNV(hitObj_0, uint(idx_0), _S4.Origin_0, _S4.TMin_0, _S4.Direction_0, _S4.TMax_0); - RayDesc_0 _S5 = ray_0; + hitObjectRecordMissNV(hitObj_0, uint(idx_0), ray_0.Origin_0, ray_0.TMin_0, ray_0.Direction_0, ray_0.TMax_0); hitObjectNV hitObj_1; - hitObjectRecordMissNV(hitObj_1, uint(idx_0 + 1), _S5.Origin_0, _S5.TMin_0, _S5.Direction_0, _S5.TMax_0); - bool _S6 = (hitObjectIsMissNV((hitObj_1))); - uint _S7 = uint(int(_S6)); - ((outputBuffer_0)._data[(uint(idx_0))]) = _S7; + hitObjectRecordMissNV(hitObj_1, uint(idx_0 + 1), ray_0.Origin_0, ray_0.TMin_0, ray_0.Direction_0, ray_0.TMax_0); + bool _S4 = (hitObjectIsMissNV((hitObj_1))); + uint _S5 = uint(int(_S4)); + ((outputBuffer_0)._data[(uint(idx_0))]) = _S5; return; } diff --git a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-hit.slang.1.expected b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-hit.slang.1.expected index 847eab926..09e389c32 100644 --- a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-hit.slang.1.expected +++ b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-hit.slang.1.expected @@ -55,17 +55,16 @@ uint calcValue_0(hitObjectNV hit_0) uint geometryIndex_0 = (hitObjectGetGeometryIndexNV((hit_0))); uint primitiveIndex_0 = (hitObjectGetPrimitiveIndexNV((hit_0))); uint hitKind_0 = (hitObjectGetHitKindNV((hit_0))); - uint r_1 = 0U + hitKind_0 + instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0; + uint r_1 = hitKind_0 + instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0; RayDesc_0 ray_1 = HitObject_GetRayDesc_0(hit_0); - float _S6 = ray_1.TMin_0; - uint r_2 = r_1 + uint(_S6 > 0.00000000000000000000) + uint(ray_1.TMax_0 < _S6); + uint r_2 = r_1 + uint(ray_1.TMin_0 > 0.0) + uint(ray_1.TMax_0 < ray_1.TMin_0); SomeValues_0 objSomeValues_0 = HitObject_GetAttributes_0(hit_0); r_0 = r_2 + uint(objSomeValues_0.a_0); } else { - bool _S7 = (hitObjectIsMissNV((hit_0))); - if(_S7) + bool _S6 = (hitObjectIsMissNV((hit_0))); + if(_S6) { r_0 = 1U; } @@ -77,29 +76,29 @@ uint calcValue_0(hitObjectNV hit_0) return r_0; } -layout(std430, binding = 1) buffer _S8 { +layout(std430, binding = 1) buffer _S7 { uint _data[]; } outputBuffer_0; void main() { - uvec3 _S9 = ((gl_LaunchIDEXT)); - ivec2 launchID_0 = ivec2(_S9.xy); - uvec3 _S10 = ((gl_LaunchSizeEXT)); + uvec3 _S8 = ((gl_LaunchIDEXT)); + ivec2 launchID_0 = ivec2(_S8.xy); + uvec3 _S9 = ((gl_LaunchSizeEXT)); int idx_0 = launchID_0.x; RayDesc_0 ray_2; - ray_2.Origin_0 = vec3(float(idx_0), 0.00000000000000000000, 0.00000000000000000000); + ray_2.Origin_0 = vec3(float(idx_0), 0.0, 0.0); ray_2.TMin_0 = 0.00999999977648258209; - ray_2.Direction_0 = vec3(0.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000); - ray_2.TMax_0 = 10000.00000000000000000000; - RayDesc_0 _S11 = ray_2; + ray_2.Direction_0 = vec3(0.0, 1.0, 0.0); + ray_2.TMax_0 = 10000.0; + RayDesc_0 _S10 = ray_2; hitObjectNV hitObj_0; - hitObjectRecordHitWithIndexNV(hitObj_0, scene_0, int(uint(idx_0)), int(uint(idx_0 * 2)), int(uint(idx_0 * 3)), 0U, 0U, _S11.Origin_0, _S11.TMin_0, _S11.Direction_0, _S11.TMax_0, (0)); + hitObjectRecordHitWithIndexNV(hitObj_0, scene_0, int(uint(idx_0)), int(uint(idx_0 * 2)), int(uint(idx_0 * 3)), 0U, 0U, _S10.Origin_0, _S10.TMin_0, _S10.Direction_0, _S10.TMax_0, (0)); uint r_3 = calcValue_0(hitObj_0); - RayDesc_0 _S12 = ray_2; + RayDesc_0 _S11 = ray_2; hitObjectNV hitObj_1; - hitObjectRecordHitNV(hitObj_1, scene_0, int(uint(idx_0)), int(uint(idx_0 * 3)), int(uint(idx_0 * 2)), 0U, 0U, 4U, _S12.Origin_0, _S12.TMin_0, _S12.Direction_0, _S12.TMax_0, (0)); - uint _S13 = calcValue_0(hitObj_1); - uint r_4 = r_3 + _S13; + hitObjectRecordHitNV(hitObj_1, scene_0, int(uint(idx_0)), int(uint(idx_0 * 3)), int(uint(idx_0 * 2)), 0U, 0U, 4U, _S11.Origin_0, _S11.TMin_0, _S11.Direction_0, _S11.TMax_0, (0)); + uint _S12 = calcValue_0(hitObj_1); + uint r_4 = r_3 + _S12; ((outputBuffer_0)._data[(uint(idx_0))]) = r_4; return; } diff --git a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-miss.slang.1.expected b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-miss.slang.1.expected index 33eb46da3..2bedf5743 100644 --- a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-miss.slang.1.expected +++ b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-make-miss.slang.1.expected @@ -23,16 +23,15 @@ void main() { int idx_0 = int(gl_GlobalInvocationID.x); RayDesc_0 ray_0; - ray_0.Origin_0 = vec3(float(idx_0), 0.00000000000000000000, 0.00000000000000000000); + ray_0.Origin_0 = vec3(float(idx_0), 0.0, 0.0); ray_0.TMin_0 = 0.00999999977648258209; - ray_0.Direction_0 = vec3(0.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000); - ray_0.TMax_0 = 10000.00000000000000000000; - RayDesc_0 _S2 = ray_0; + ray_0.Direction_0 = vec3(0.0, 1.0, 0.0); + ray_0.TMax_0 = 10000.0; hitObjectNV hitObj_0; - hitObjectRecordMissNV(hitObj_0, uint(idx_0), _S2.Origin_0, _S2.TMin_0, _S2.Direction_0, _S2.TMax_0); - bool _S3 = (hitObjectIsMissNV((hitObj_0))); - uint _S4 = uint(int(_S3)); - ((outputBuffer_0)._data[(uint(idx_0))]) = _S4; + hitObjectRecordMissNV(hitObj_0, uint(idx_0), ray_0.Origin_0, ray_0.TMin_0, ray_0.Direction_0, ray_0.TMax_0); + bool _S2 = (hitObjectIsMissNV((hitObj_0))); + uint _S3 = uint(int(_S2)); + ((outputBuffer_0)._data[(uint(idx_0))]) = _S3; return; } diff --git a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-reorder-thread.slang.1.expected b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-reorder-thread.slang.1.expected index f250c1c92..58f06cfec 100644 --- a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-reorder-thread.slang.1.expected +++ b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-reorder-thread.slang.1.expected @@ -41,7 +41,7 @@ uint calcValue_0(hitObjectNV hit_0) uint geometryIndex_0 = (hitObjectGetGeometryIndexNV((hit_0))); uint primitiveIndex_0 = (hitObjectGetPrimitiveIndexNV((hit_0))); SomeValues_0 objSomeValues_0 = HitObject_GetAttributes_0(hit_0); - r_0 = 0U + instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0 + uint(objSomeValues_0.a_0); + r_0 = instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0 + uint(objSomeValues_0.a_0); } else { @@ -80,36 +80,40 @@ void main() uvec3 _S4 = ((gl_LaunchSizeEXT)); int idx_0 = launchID_0.x; float _S5 = float(idx_0); - SomeValues_0 someValues_0 = { idx_0, _S5 * 2.00000000000000000000 }; + float _S6 = _S5 * 2.0; RayDesc_0 ray_0; - ray_0.Origin_0 = vec3(_S5, 0.00000000000000000000, 0.00000000000000000000); + ray_0.Origin_0 = vec3(_S5, 0.0, 0.0); ray_0.TMin_0 = 0.00999999977648258209; - ray_0.Direction_0 = vec3(0.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000); - ray_0.TMax_0 = 10000.00000000000000000000; - RayDesc_0 _S6 = ray_0; - p_0 = someValues_0; + ray_0.Direction_0 = vec3(0.0, 1.0, 0.0); + ray_0.TMax_0 = 10000.0; + RayDesc_0 _S7 = ray_0; + p_0.a_0 = idx_0; + p_0.b_0 = _S6; hitObjectNV hitObj_0; - hitObjectTraceRayNV(hitObj_0, scene_0, 20U, 255U, 0U, 4U, 0U, _S6.Origin_0, _S6.TMin_0, _S6.Direction_0, _S6.TMax_0, (0)); + hitObjectTraceRayNV(hitObj_0, scene_0, 20U, 255U, 0U, 4U, 0U, _S7.Origin_0, _S7.TMin_0, _S7.Direction_0, _S7.TMax_0, (0)); uint r_1 = calcValue_0(hitObj_0); reorderThreadNV(hitObj_0); + float _S8 = _S5 * 4.0; SomeValues_0 otherValues_0; - SomeValues_0 _S7 = { idx_0 * -1, _S5 * 4.00000000000000000000 }; - otherValues_0 = _S7; + otherValues_0.a_0 = idx_0 * -1; + otherValues_0.b_0 = _S8; HitObject_Invoke_0(scene_0, hitObj_0, otherValues_0); - uint _S8 = calcValue_0(hitObj_0); - uint r_2 = r_1 + _S8; + uint _S9 = calcValue_0(hitObj_0); + uint r_2 = r_1 + _S9; reorderThreadNV(hitObj_0, uint(idx_0 & 3), 2U); - SomeValues_0 _S9 = { idx_0 * -2, _S5 * 8.00000000000000000000 }; - otherValues_0 = _S9; + float _S10 = _S5 * 8.0; + otherValues_0.a_0 = idx_0 * -2; + otherValues_0.b_0 = _S10; HitObject_Invoke_0(scene_0, hitObj_0, otherValues_0); - uint _S10 = calcValue_0(hitObj_0); - uint r_3 = r_2 + _S10; + uint _S11 = calcValue_0(hitObj_0); + uint r_3 = r_2 + _S11; reorderThreadNV(uint(idx_0 & 1), 1U); - SomeValues_0 _S11 = { idx_0 * -4, _S5 * 16.00000000000000000000 }; - otherValues_0 = _S11; + float _S12 = _S5 * 16.0; + otherValues_0.a_0 = idx_0 * -4; + otherValues_0.b_0 = _S12; HitObject_Invoke_0(scene_0, hitObj_0, otherValues_0); - uint _S12 = calcValue_0(hitObj_0); - uint r_4 = r_3 + _S12; + uint _S13 = calcValue_0(hitObj_0); + uint r_4 = r_3 + _S13; ((outputBuffer_0)._data[(uint(idx_0))]) = r_4; return; } diff --git a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-motion-ray.slang.1.expected b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-motion-ray.slang.1.expected index f6f6f132d..e6d31a3c8 100644 --- a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-motion-ray.slang.1.expected +++ b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-motion-ray.slang.1.expected @@ -42,7 +42,7 @@ uint calcValue_0(hitObjectNV hit_0) uint geometryIndex_0 = (hitObjectGetGeometryIndexNV((hit_0))); uint primitiveIndex_0 = (hitObjectGetPrimitiveIndexNV((hit_0))); SomeValues_0 objSomeValues_0 = HitObject_GetAttributes_0(hit_0); - r_0 = 0U + instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0 + uint(objSomeValues_0.a_0); + r_0 = instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0 + uint(objSomeValues_0.a_0); } else { @@ -71,19 +71,20 @@ void main() int _S5 = idx_0 / 4; float currentTime_0 = float(_S5); float _S6 = float(idx_0); - SomeValues_0 someValues_0 = { idx_0, _S6 * 2.00000000000000000000 }; + float _S7 = _S6 * 2.0; RayDesc_0 ray_0; - ray_0.Origin_0 = vec3(_S6, 0.00000000000000000000, 0.00000000000000000000); + ray_0.Origin_0 = vec3(_S6, 0.0, 0.0); ray_0.TMin_0 = 0.00999999977648258209; - ray_0.Direction_0 = vec3(0.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000); - ray_0.TMax_0 = 10000.00000000000000000000; - RayDesc_0 _S7 = ray_0; - p_0 = someValues_0; + ray_0.Direction_0 = vec3(0.0, 1.0, 0.0); + ray_0.TMax_0 = 10000.0; + RayDesc_0 _S8 = ray_0; + p_0.a_0 = idx_0; + p_0.b_0 = _S7; hitObjectNV hitObj_0; - hitObjectTraceRayMotionNV(hitObj_0, scene_0, 20U, 255U, 0U, 4U, 0U, _S7.Origin_0, _S7.TMin_0, _S7.Direction_0, _S7.TMax_0, currentTime_0, (0)); - uint _S8 = uint(idx_0); - uint _S9 = calcValue_0(hitObj_0); - ((outputBuffer_0)._data[(_S8)]) = _S9; + hitObjectTraceRayMotionNV(hitObj_0, scene_0, 20U, 255U, 0U, 4U, 0U, _S8.Origin_0, _S8.TMin_0, _S8.Direction_0, _S8.TMax_0, currentTime_0, (0)); + uint _S9 = uint(idx_0); + uint _S10 = calcValue_0(hitObj_0); + ((outputBuffer_0)._data[(_S9)]) = _S10; return; } diff --git a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-ray.slang.1.expected b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-ray.slang.1.expected index 16099b5e2..9b5a4d193 100644 --- a/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-ray.slang.1.expected +++ b/tests/hlsl-intrinsic/shader-execution-reordering/hit-object-trace-ray.slang.1.expected @@ -41,7 +41,7 @@ uint calcValue_0(hitObjectNV hit_0) uint geometryIndex_0 = (hitObjectGetGeometryIndexNV((hit_0))); uint primitiveIndex_0 = (hitObjectGetPrimitiveIndexNV((hit_0))); SomeValues_0 objSomeValues_0 = HitObject_GetAttributes_0(hit_0); - r_0 = 0U + instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0 + uint(objSomeValues_0.a_0); + r_0 = instanceIndex_0 + instanceID_0 + geometryIndex_0 + primitiveIndex_0 + uint(objSomeValues_0.a_0); } else { @@ -68,19 +68,20 @@ void main() uvec3 _S4 = ((gl_LaunchSizeEXT)); int idx_0 = launchID_0.x; float _S5 = float(idx_0); - SomeValues_0 someValues_0 = { idx_0, _S5 * 2.00000000000000000000 }; + float _S6 = _S5 * 2.0; RayDesc_0 ray_0; - ray_0.Origin_0 = vec3(_S5, 0.00000000000000000000, 0.00000000000000000000); + ray_0.Origin_0 = vec3(_S5, 0.0, 0.0); ray_0.TMin_0 = 0.00999999977648258209; - ray_0.Direction_0 = vec3(0.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000); - ray_0.TMax_0 = 10000.00000000000000000000; - RayDesc_0 _S6 = ray_0; - p_0 = someValues_0; + ray_0.Direction_0 = vec3(0.0, 1.0, 0.0); + ray_0.TMax_0 = 10000.0; + RayDesc_0 _S7 = ray_0; + p_0.a_0 = idx_0; + p_0.b_0 = _S6; hitObjectNV hitObj_0; - hitObjectTraceRayNV(hitObj_0, scene_0, 20U, 255U, 0U, 4U, 0U, _S6.Origin_0, _S6.TMin_0, _S6.Direction_0, _S6.TMax_0, (0)); - uint _S7 = uint(idx_0); - uint _S8 = calcValue_0(hitObj_0); - ((outputBuffer_0)._data[(_S7)]) = _S8; + hitObjectTraceRayNV(hitObj_0, scene_0, 20U, 255U, 0U, 4U, 0U, _S7.Origin_0, _S7.TMin_0, _S7.Direction_0, _S7.TMax_0, (0)); + uint _S8 = uint(idx_0); + uint _S9 = calcValue_0(hitObj_0); + ((outputBuffer_0)._data[(_S8)]) = _S9; return; } diff --git a/tests/nv-extensions/nv-ray-tracing-motion-blur.slang.glsl b/tests/nv-extensions/nv-ray-tracing-motion-blur.slang.glsl index bad4dd370..79c6232f3 100644 --- a/tests/nv-extensions/nv-ray-tracing-motion-blur.slang.glsl +++ b/tests/nv-extensions/nv-ray-tracing-motion-blur.slang.glsl @@ -55,11 +55,9 @@ struct RayDesc_0 void TraceMotionRay_0(accelerationStructureEXT AccelerationStructure_0, uint RayFlags_0, uint InstanceInclusionMask_0, uint RayContributionToHitGroupIndex_0, uint MultiplierForGeometryContributionToHitGroupIndex_0, uint MissShaderIndex_0, RayDesc_0 Ray_0, float CurrentTime_0, inout ShadowRay_0 Payload_0) { p_0 = Payload_0; - traceRayMotionNV(AccelerationStructure_0, RayFlags_0, InstanceInclusionMask_0, RayContributionToHitGroupIndex_0, MultiplierForGeometryContributionToHitGroupIndex_0, MissShaderIndex_0, Ray_0.Origin_0, Ray_0.TMin_0, Ray_0.Direction_0, Ray_0.TMax_0, CurrentTime_0, (0)); Payload_0 = p_0; - return; } @@ -68,7 +66,7 @@ uniform accelerationStructureEXT as_0; float saturate_0(float x_0) { - float _S2 = clamp(x_0, float(0), float(1)); + float _S2 = clamp(x_0, 0.0, 1.0); return _S2; } @@ -85,11 +83,9 @@ ReflectionRay_0 p_1; void TraceRay_0(accelerationStructureEXT AccelerationStructure_1, uint RayFlags_1, uint InstanceInclusionMask_1, uint RayContributionToHitGroupIndex_1, uint MultiplierForGeometryContributionToHitGroupIndex_1, uint MissShaderIndex_1, RayDesc_0 Ray_1, inout ReflectionRay_0 Payload_1) { p_1 = Payload_1; - traceRayEXT(AccelerationStructure_1, RayFlags_1, InstanceInclusionMask_1, RayContributionToHitGroupIndex_1, MultiplierForGeometryContributionToHitGroupIndex_1, MissShaderIndex_1, Ray_1.Origin_0, Ray_1.TMin_0, Ray_1.Direction_0, Ray_1.TMax_0, (1)); Payload_1 = p_1; - return; } @@ -99,8 +95,6 @@ uniform image2D outputImage_0; void main() { - float atten_0; - uvec3 _S3 = ((gl_LaunchIDEXT)); ivec2 launchID_0 = ivec2(_S3.xy); @@ -108,8 +102,8 @@ void main() ivec2 launchSize_0 = ivec2(_S4.xy); - float _S5 = (float(launchID_0.x) + 0.50000000000000000000) / float(launchSize_0.x); - float _S6 = (float(launchID_0.y) + 0.50000000000000000000) / float(launchSize_0.y); + float _S5 = (float(launchID_0.x) + 0.5) / float(launchSize_0.x); + float _S6 = (float(launchID_0.y) + 0.5) / float(launchSize_0.y); vec2 inUV_0 = vec2(_S5, _S6); @@ -118,27 +112,28 @@ void main() vec3 P_0 = _S7.xyz; vec4 _S8 = (texture(sampler2D(samplerNormal_0,sampler_0), (inUV_0))); - vec3 N_0 = _S8.xyz * 2.00000000000000000000 - 1.00000000000000000000; + vec3 N_0 = _S8.xyz * 2.0 - 1.0; vec3 lightDelta_0 = ubo_0._data.light_0.position_0.xyz - P_0; float lightDist_0 = length(lightDelta_0); vec3 L_0 = normalize(lightDelta_0); - float _S9 = 1.00000000000000000000 / (lightDist_0 * lightDist_0); + float _S9 = 1.0 / (lightDist_0 * lightDist_0); RayDesc_0 ray_0; ray_0.Origin_0 = P_0; - ray_0.TMin_0 = 0.00000100000000000000; + ray_0.TMin_0 = 0.00000099999999747524; ray_0.Direction_0 = lightDelta_0; ray_0.TMax_0 = lightDist_0; ShadowRay_0 shadowRay_0; - shadowRay_0.hitDistance_0 = float(0); + shadowRay_0.hitDistance_0 = 0.0; + TraceMotionRay_0(as_0, 1U, 255U, 0U, 0U, 2U, ray_0, 1.0, shadowRay_0); - TraceMotionRay_0(as_0, uint(1), uint(255), uint(0), uint(0), uint(2), ray_0, float(1), shadowRay_0); + float atten_0; if(shadowRay_0.hitDistance_0 < lightDist_0) { - atten_0 = 0.00000000000000000000; + atten_0 = 0.0; } else { @@ -154,8 +149,8 @@ void main() vec3 color_2 = _S10 * _S12 * atten_0; ReflectionRay_0 reflectionRay_0; - TraceRay_0(as_0, uint(1), uint(255), uint(0), uint(0), uint(2), ray_0, reflectionRay_0); + TraceRay_0(as_0, 1U, 255U, 0U, 0U, 2U, ray_0, reflectionRay_0); - imageStore((outputImage_0), ivec2((uvec2(launchID_0))), vec4(color_2 + reflectionRay_0.color_1, 1.00000000000000000000)); + imageStore((outputImage_0), ivec2((uvec2(launchID_0))), vec4(color_2 + reflectionRay_0.color_1, 1.0)); return; }
\ No newline at end of file diff --git a/tests/pipeline/rasterization/mesh/hello.slang.glsl b/tests/pipeline/rasterization/mesh/hello.slang.glsl index c2c35915a..3a0848dcb 100644 --- a/tests/pipeline/rasterization/mesh/hello.slang.glsl +++ b/tests/pipeline/rasterization/mesh/hello.slang.glsl @@ -2,8 +2,9 @@ #extension GL_EXT_mesh_shader : require layout(row_major) uniform; layout(row_major) buffer; -const vec3 colors_0[3] = { vec3(1.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000), vec3(0.00000000000000000000, 1.00000000000000000000, 1.00000000000000000000), vec3(1.00000000000000000000, 0.00000000000000000000, 1.00000000000000000000) }; -const vec2 positions_0[3] = { vec2(0.00000000000000000000, -0.50000000000000000000), vec2(0.50000000000000000000, 0.50000000000000000000), vec2(-0.50000000000000000000, 0.50000000000000000000) }; +const vec3 colors_0[3] = { vec3(1.0, 1.0, 0.0), vec3(0.0, 1.0, 1.0), vec3(1.0, 0.0, 1.0) }; +const vec2 positions_0[3] = { vec2(0.0, -0.5), vec2(0.5, 0.5), vec2(-0.5, 0.5) }; + layout(location = 0) out vec3 _S1[3]; @@ -23,9 +24,8 @@ void main() SetMeshOutputsEXT(3U, 1U); if(gl_LocalInvocationIndex < 3U) { - vec3 _S2 = colors_0[gl_LocalInvocationIndex]; - gl_MeshVerticesEXT[gl_LocalInvocationIndex].gl_Position = vec4(positions_0[gl_LocalInvocationIndex], 0.00000000000000000000, 1.00000000000000000000); - _S1[gl_LocalInvocationIndex] = _S2; + gl_MeshVerticesEXT[gl_LocalInvocationIndex].gl_Position = vec4(positions_0[gl_LocalInvocationIndex], 0.0, 1.0); + _S1[gl_LocalInvocationIndex] = colors_0[gl_LocalInvocationIndex]; } else { diff --git a/tests/pipeline/rasterization/mesh/hello.slang.hlsl b/tests/pipeline/rasterization/mesh/hello.slang.hlsl index ea41895b1..a10dc6884 100644 --- a/tests/pipeline/rasterization/mesh/hello.slang.hlsl +++ b/tests/pipeline/rasterization/mesh/hello.slang.hlsl @@ -2,24 +2,26 @@ #ifdef SLANG_HLSL_ENABLE_NVAPI #include "nvHLSLExtns.h" #endif +#pragma warning(disable: 3557) -static const float3 colors_0[int(3)] = { float3(1.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000), float3(0.00000000000000000000, 1.00000000000000000000, 1.00000000000000000000), float3(1.00000000000000000000, 0.00000000000000000000, 1.00000000000000000000) }; -static const float2 positions_0[int(3)] = { float2(0.00000000000000000000, -0.50000000000000000000), float2(0.50000000000000000000, 0.50000000000000000000), float2(-0.50000000000000000000, 0.50000000000000000000) }; +static const float3 colors_0[int(3)] = { float3(1.0, 1.0, 0.0), float3(0.0, 1.0, 1.0), float3(1.0, 0.0, 1.0) }; +static const float2 positions_0[int(3)] = { float2(0.0, -0.5), float2(0.5, 0.5), float2(-0.5, 0.5) }; struct Vertex_0 { float4 pos_0 : SV_Position; float3 color_0 : Color; }; +[shader("mesh")] [numthreads(3, 1, 1)] [outputtopology("triangle")] -void main(uint tig_0 : SV_GROUPINDEX, vertices out Vertex_0 verts_0[int(3)], indices out uint3 triangles_0[int(1)]) +void main(uint tig_0 : SV_GROUPINDEX, vertices vertices out Vertex_0 verts_0[int(3)], indices indices out uint3 triangles_0[int(1)]) { SetMeshOutputCounts(3U, 1U); if(tig_0 < 3U) { - Vertex_0 _S1 = { float4(positions_0[tig_0], 0.00000000000000000000, 1.00000000000000000000), colors_0[tig_0] }; - verts_0[tig_0] = _S1; + verts_0[tig_0].pos_0 = float4(positions_0[tig_0], 0.0, 1.0); + verts_0[tig_0].color_0 = colors_0[tig_0]; } else { diff --git a/tests/pipeline/rasterization/mesh/hlsl-syntax.slang.glsl b/tests/pipeline/rasterization/mesh/hlsl-syntax.slang.glsl index 96d681c5c..5e059a8a3 100644 --- a/tests/pipeline/rasterization/mesh/hlsl-syntax.slang.glsl +++ b/tests/pipeline/rasterization/mesh/hlsl-syntax.slang.glsl @@ -2,8 +2,8 @@ #extension GL_EXT_mesh_shader : require layout(row_major) uniform; layout(row_major) buffer; -const vec3 colors_0[3] = { vec3(1.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000), vec3(0.00000000000000000000, 1.00000000000000000000, 1.00000000000000000000), vec3(1.00000000000000000000, 0.00000000000000000000, 1.00000000000000000000) }; -const vec2 positions_0[3] = { vec2(0.00000000000000000000, -0.50000000000000000000), vec2(0.50000000000000000000, 0.50000000000000000000), vec2(-0.50000000000000000000, 0.50000000000000000000) }; +const vec3 colors_0[3] = { vec3(1.0, 1.0, 0.0), vec3(0.0, 1.0, 1.0), vec3(1.0, 0.0, 1.0) }; +const vec2 positions_0[3] = { vec2(0.0, -0.5), vec2(0.5, 0.5), vec2(-0.5, 0.5) }; layout(location = 0) out vec3 _S1[3]; @@ -13,13 +13,13 @@ out gl_MeshPerVertexEXT } gl_MeshVerticesEXT[3]; +out uvec3 gl_PrimitiveTriangleIndicesEXT[1]; void foo_0(uint _S2) { if(_S2 < 3U) { - vec3 _S3 = colors_0[_S2]; - gl_MeshVerticesEXT[_S2].gl_Position = vec4(positions_0[_S2], 0.00000000000000000000, 1.00000000000000000000); - _S1[_S2] = _S3; + gl_MeshVerticesEXT[_S2].gl_Position = vec4(positions_0[_S2], 0.0, 1.0); + _S1[_S2] = colors_0[_S2]; } else { diff --git a/tests/pipeline/rasterization/mesh/passing-outputs.slang.glsl b/tests/pipeline/rasterization/mesh/passing-outputs.slang.glsl index db8a69ef3..31c2f0db2 100644 --- a/tests/pipeline/rasterization/mesh/passing-outputs.slang.glsl +++ b/tests/pipeline/rasterization/mesh/passing-outputs.slang.glsl @@ -17,57 +17,65 @@ struct Vertex_0 void just_two_0(out Vertex_0 v_0, out Vertex_0 w_0) { - Texes_0 _S1 = { vec2(0.00000000000000000000, 0.00000000000000000000), vec4(0.00000000000000000000, 0.00000000000000000000, 0.00000000000000000000, 0.00000000000000000000) }; - Vertex_0 _S2 = { vec4(0.00000000000000000000), vec3(1.00000000000000000000), _S1 }; - v_0 = _S2; - w_0 = v_0; + const vec4 _S1 = vec4(0.0); + const vec3 _S2 = vec3(1.0); + Texes_0 _S3 = { vec2(0.0, 0.0), vec4(0.0, 0.0, 0.0, 0.0) }; + v_0.pos_0 = _S1; + v_0.col_0 = _S2; + v_0.ts_0 = _S3; + w_0.pos_0 = _S1; + w_0.col_0 = _S2; + w_0.ts_0 = _S3; return; } void just_one_0(out Vertex_0 v_1) { - Texes_0 _S3 = { vec2(0.00000000000000000000, 0.00000000000000000000), vec4(0.00000000000000000000, 0.00000000000000000000, 0.00000000000000000000, 0.00000000000000000000) }; - Vertex_0 _S4 = { vec4(0.00000000000000000000), vec3(1.00000000000000000000), _S3 }; - v_1 = _S4; + const vec3 _S4 = vec3(1.0); + Texes_0 _S5 = { vec2(0.0, 0.0), vec4(0.0, 0.0, 0.0, 0.0) }; + v_1.pos_0 = vec4(0.0); + v_1.col_0 = _S4; + v_1.ts_0 = _S5; return; } void part_of_one_0(out vec4 p_0) { - p_0 = vec4(1.00000000000000000000, 2.00000000000000000000, 3.00000000000000000000, 4.00000000000000000000); + p_0 = vec4(1.0, 2.0, 3.0, 4.0); return; } void write_struct_0(out Texes_0 t_0) { - t_0.tex1_0 = vec2(0.00000000000000000000); - t_0.tex2_0 = vec4(1.00000000000000000000); + t_0.tex1_0 = vec2(0.0); + t_0.tex2_0 = vec4(1.0); return; } layout(location = 0) -out vec3 _S5[3]; +out vec3 _S6[3]; layout(location = 1) -out vec2 _S6[3]; +out vec2 _S7[3]; layout(location = 2) -out vec4 _S7[3]; +out vec4 _S8[3]; out gl_MeshPerVertexEXT { vec4 gl_Position; } gl_MeshVerticesEXT[3]; +out uvec3 gl_PrimitiveTriangleIndicesEXT[1]; void everything_0() { - vec3 _S8 = vec3(1.00000000000000000000); - vec2 _S9 = vec2(0.00000000000000000000, 0.00000000000000000000); - vec4 _S10 = vec4(0.00000000000000000000, 0.00000000000000000000, 0.00000000000000000000, 0.00000000000000000000); - gl_MeshVerticesEXT[0U].gl_Position = vec4(0.00000000000000000000); - _S5[0U] = _S8; + vec3 _S9 = vec3(1.0); + vec2 _S10 = vec2(0.0, 0.0); + vec4 _S11 = vec4(0.0, 0.0, 0.0, 0.0); + gl_MeshVerticesEXT[0U].gl_Position = vec4(0.0); _S6[0U] = _S9; _S7[0U] = _S10; + _S8[0U] = _S11; return; } @@ -79,66 +87,61 @@ void a_0() void b_0() { - Vertex_0 _S11; Vertex_0 _S12; - just_two_0(_S12, _S11); - Vertex_0 _S13 = _S12; + Vertex_0 _S13; + just_two_0(_S13, _S12); + Vertex_0 _S14 = _S13; gl_MeshVerticesEXT[0U].gl_Position = _S13.pos_0; - _S5[0U] = _S13.col_0; - Texes_0 _S14 = _S13.ts_0; - _S6[0U] = _S14.tex1_0; - _S7[0U] = _S14.tex2_0; - Vertex_0 _S15 = _S11; - gl_MeshVerticesEXT[0U].gl_Position = _S15.pos_0; - _S5[0U] = _S15.col_0; - Texes_0 _S16 = _S15.ts_0; - _S6[0U] = _S16.tex1_0; - _S7[0U] = _S16.tex2_0; + _S6[0U] = _S14.col_0; + _S7[0U] = _S14.ts_0.tex1_0; + _S8[0U] = _S14.ts_0.tex2_0; + Vertex_0 _S15 = _S12; + gl_MeshVerticesEXT[0U].gl_Position = _S12.pos_0; + _S6[0U] = _S15.col_0; + _S7[0U] = _S15.ts_0.tex1_0; + _S8[0U] = _S15.ts_0.tex2_0; return; } -void c_0(uint _S17) +void c_0(uint _S16) { - Vertex_0 _S18; - just_one_0(_S18); - Vertex_0 _S19 = _S18; - gl_MeshVerticesEXT[_S17].gl_Position = _S19.pos_0; - _S5[_S17] = _S19.col_0; - Texes_0 _S20 = _S19.ts_0; - _S6[_S17] = _S20.tex1_0; - _S7[_S17] = _S20.tex2_0; + Vertex_0 _S17; + just_one_0(_S17); + Vertex_0 _S18 = _S17; + gl_MeshVerticesEXT[_S16].gl_Position = _S17.pos_0; + _S6[_S16] = _S18.col_0; + _S7[_S16] = _S18.ts_0.tex1_0; + _S8[_S16] = _S18.ts_0.tex2_0; return; } -void d_0(uint _S21) +void d_0(uint _S19) { - Vertex_0 _S22; - Vertex_0 _S23; - just_two_0(_S23, _S22); - Vertex_0 _S24 = _S23; - gl_MeshVerticesEXT[_S21].gl_Position = _S24.pos_0; - _S5[_S21] = _S24.col_0; - Texes_0 _S25 = _S24.ts_0; - _S6[_S21] = _S25.tex1_0; - _S7[_S21] = _S25.tex2_0; - Vertex_0 _S26 = _S22; - gl_MeshVerticesEXT[0U].gl_Position = _S26.pos_0; - _S5[0U] = _S26.col_0; - Texes_0 _S27 = _S26.ts_0; - _S6[0U] = _S27.tex1_0; - _S7[0U] = _S27.tex2_0; + Vertex_0 _S20; + Vertex_0 _S21; + just_two_0(_S21, _S20); + Vertex_0 _S22 = _S21; + gl_MeshVerticesEXT[_S19].gl_Position = _S21.pos_0; + _S6[_S19] = _S22.col_0; + _S7[_S19] = _S22.ts_0.tex1_0; + _S8[_S19] = _S22.ts_0.tex2_0; + Vertex_0 _S23 = _S20; + gl_MeshVerticesEXT[0U].gl_Position = _S20.pos_0; + _S6[0U] = _S23.col_0; + _S7[0U] = _S23.ts_0.tex1_0; + _S8[0U] = _S23.ts_0.tex2_0; return; } -void e_0(uint _S28) +void e_0(uint _S24) { - part_of_one_0(gl_MeshVerticesEXT[_S28].gl_Position); - Texes_0 _S29; - write_struct_0(_S29); - Texes_0 _S30 = _S29; - _S6[_S28] = _S30.tex1_0; - _S7[_S28] = _S30.tex2_0; - part_of_one_0(_S7[_S28]); + part_of_one_0(gl_MeshVerticesEXT[_S24].gl_Position); + Texes_0 _S25; + write_struct_0(_S25); + Texes_0 _S26 = _S25; + _S7[_S24] = _S25.tex1_0; + _S8[_S24] = _S26.tex2_0; + part_of_one_0(_S8[_S24]); return; } diff --git a/tests/pipeline/rasterization/mesh/primitive-output.slang.glsl b/tests/pipeline/rasterization/mesh/primitive-output.slang.glsl index 6ff2dbce8..35efcf4af 100644 --- a/tests/pipeline/rasterization/mesh/primitive-output.slang.glsl +++ b/tests/pipeline/rasterization/mesh/primitive-output.slang.glsl @@ -2,8 +2,9 @@ #extension GL_EXT_mesh_shader : require layout(row_major) uniform; layout(row_major) buffer; -const vec3 colors_0[3] = { vec3(1.00000000000000000000, 1.00000000000000000000, 0.00000000000000000000), vec3(0.00000000000000000000, 1.00000000000000000000, 1.00000000000000000000), vec3(1.00000000000000000000, 0.00000000000000000000, 1.00000000000000000000) }; -const vec2 positions_0[3] = { vec2(0.00000000000000000000, -0.50000000000000000000), vec2(0.50000000000000000000, 0.50000000000000000000), vec2(-0.50000000000000000000, 0.50000000000000000000) }; +const vec3 colors_0[3] = { vec3(1.0, 1.0, 0.0), vec3(0.0, 1.0, 1.0), vec3(1.0, 0.0, 1.0) }; +const vec2 positions_0[3] = { vec2(0.0, -0.5), vec2(0.5, 0.5), vec2(-0.5, 0.5) }; +out uvec3 gl_PrimitiveTriangleIndicesEXT[1]; layout(location = 0) out vec3 _S1[3]; @@ -30,9 +31,8 @@ void main() SetMeshOutputsEXT(3U, 1U); if(gl_LocalInvocationIndex < 3U) { - vec3 _S3 = colors_0[gl_LocalInvocationIndex]; - gl_MeshVerticesEXT[gl_LocalInvocationIndex].gl_Position = vec4(positions_0[gl_LocalInvocationIndex], 0.00000000000000000000, 1.00000000000000000000); - _S1[gl_LocalInvocationIndex] = _S3; + gl_MeshVerticesEXT[gl_LocalInvocationIndex].gl_Position = vec4(positions_0[gl_LocalInvocationIndex], 0.0, 1.0); + _S1[gl_LocalInvocationIndex] = colors_0[gl_LocalInvocationIndex]; } else { @@ -40,7 +40,7 @@ void main() if(gl_LocalInvocationIndex < 1U) { gl_PrimitiveTriangleIndicesEXT[gl_LocalInvocationIndex] = uvec3(0U, 1U, 2U); - _S2[gl_LocalInvocationIndex] = vec3(0.00000000000000000000, 0.00000000000000000000, 1.00000000000000000000); + _S2[gl_LocalInvocationIndex] = vec3(0.0, 0.0, 1.0); gl_MeshPrimitivesEXT[gl_LocalInvocationIndex].gl_PrimitiveID = int(gl_LocalInvocationIndex); gl_MeshPrimitivesEXT[gl_LocalInvocationIndex].gl_CullPrimitiveEXT = false; } diff --git a/tests/pipeline/ray-tracing/trace-ray-inline.slang.glsl b/tests/pipeline/ray-tracing/trace-ray-inline.slang.glsl index 389dae05a..04ef5a6fe 100644 --- a/tests/pipeline/ray-tracing/trace-ray-inline.slang.glsl +++ b/tests/pipeline/ray-tracing/trace-ray-inline.slang.glsl @@ -74,8 +74,7 @@ void main() rayQueryEXT query_0; MyRayPayload_0 payload_5; - MyRayPayload_0 _S2 = { -1 }; - payload_5 = _S2; + payload_5.value_1 = -1; rayQueryInitializeEXT((query_0), (myAccelerationStructure_0), (C_0._data.rayFlags_0 | 512), (C_0._data.instanceMask_0), (C_0._data.origin_0), (C_0._data.tMin_0), (C_0._data.direction_0), (C_0._data.tMax_0)); MyProceduralHitAttrs_0 committedProceduralAttrs_0; @@ -83,37 +82,34 @@ void main() for(;;) { - bool _S3 = rayQueryProceedEXT(query_0); + bool _S2 = rayQueryProceedEXT(query_0); - if(!_S3) + if(!_S2) { break; } - uint _S4 = (rayQueryGetIntersectionTypeEXT((query_0), false)); + uint _S3 = (rayQueryGetIntersectionTypeEXT((query_0), false)); MyProceduralHitAttrs_0 committedProceduralAttrs_1; - switch(_S4) + switch(_S3) { case 1U: { MyProceduralHitAttrs_0 candidateProceduralAttrs_0; - MyProceduralHitAttrs_0 _S5 = { 0 }; + candidateProceduralAttrs_0.value_0 = 0; + float tHit_1 = 0.0; + bool _S4 = myProceduralIntersection_0(tHit_1, candidateProceduralAttrs_0); - candidateProceduralAttrs_0 = _S5; - float tHit_1; - tHit_1 = 0.00000000000000000000; - bool _S6 = myProceduralIntersection_0(tHit_1, candidateProceduralAttrs_0); - - if(_S6) + if(_S4) { - bool _S7 = myProceduralAnyHit_0(payload_5); + bool _S5 = myProceduralAnyHit_0(payload_5); - if(_S7) + if(_S5) { rayQueryGenerateIntersectionEXT(query_0, tHit_1); - MyProceduralHitAttrs_0 _S8 = candidateProceduralAttrs_0; + MyProceduralHitAttrs_0 _S6 = candidateProceduralAttrs_0; if(C_0._data.shouldStopAtFirstHit_0 != 0U) { rayQueryTerminateEXT(query_0); @@ -122,7 +118,7 @@ void main() { } - committedProceduralAttrs_1 = _S8; + committedProceduralAttrs_1 = _S6; } else @@ -145,9 +141,9 @@ void main() case 0U: { - bool _S9 = myTriangleAnyHit_0(payload_5); + bool _S7 = myTriangleAnyHit_0(payload_5); - if(_S9) + if(_S7) { rayQueryConfirmIntersectionEXT(query_0); if(C_0._data.shouldStopAtFirstHit_0 != 0U) @@ -179,9 +175,9 @@ void main() } - uint _S10 = (rayQueryGetIntersectionTypeEXT((query_0), true)); + uint _S8 = (rayQueryGetIntersectionTypeEXT((query_0), true)); - switch(_S10) + switch(_S8) { case 1U: { |
