shader: Add IR opcode for ImageFetch
This commit is contained in:
parent
742d11c2ad
commit
b5db38f50e
|
@ -343,12 +343,14 @@ Id EmitBindlessImageSampleDrefImplicitLod(EmitContext&);
|
||||||
Id EmitBindlessImageSampleDrefExplicitLod(EmitContext&);
|
Id EmitBindlessImageSampleDrefExplicitLod(EmitContext&);
|
||||||
Id EmitBindlessImageGather(EmitContext&);
|
Id EmitBindlessImageGather(EmitContext&);
|
||||||
Id EmitBindlessImageGatherDref(EmitContext&);
|
Id EmitBindlessImageGatherDref(EmitContext&);
|
||||||
|
Id EmitBindlessImageFetch(EmitContext&);
|
||||||
Id EmitBoundImageSampleImplicitLod(EmitContext&);
|
Id EmitBoundImageSampleImplicitLod(EmitContext&);
|
||||||
Id EmitBoundImageSampleExplicitLod(EmitContext&);
|
Id EmitBoundImageSampleExplicitLod(EmitContext&);
|
||||||
Id EmitBoundImageSampleDrefImplicitLod(EmitContext&);
|
Id EmitBoundImageSampleDrefImplicitLod(EmitContext&);
|
||||||
Id EmitBoundImageSampleDrefExplicitLod(EmitContext&);
|
Id EmitBoundImageSampleDrefExplicitLod(EmitContext&);
|
||||||
Id EmitBoundImageGather(EmitContext&);
|
Id EmitBoundImageGather(EmitContext&);
|
||||||
Id EmitBoundImageGatherDref(EmitContext&);
|
Id EmitBoundImageGatherDref(EmitContext&);
|
||||||
|
Id EmitBoundImageFetch(EmitContext&);
|
||||||
Id EmitImageSampleImplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
Id EmitImageSampleImplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
||||||
Id bias_lc, Id offset);
|
Id bias_lc, Id offset);
|
||||||
Id EmitImageSampleExplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
Id EmitImageSampleExplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
||||||
|
@ -361,6 +363,8 @@ Id EmitImageGather(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id
|
||||||
Id offset2);
|
Id offset2);
|
||||||
Id EmitImageGatherDref(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
Id EmitImageGatherDref(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
||||||
Id offset, Id offset2, Id dref);
|
Id offset, Id offset2, Id dref);
|
||||||
|
Id EmitImageFetch(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords, Id offset,
|
||||||
|
Id lod, Id ms);
|
||||||
Id EmitVoteAll(EmitContext& ctx, Id pred);
|
Id EmitVoteAll(EmitContext& ctx, Id pred);
|
||||||
Id EmitVoteAny(EmitContext& ctx, Id pred);
|
Id EmitVoteAny(EmitContext& ctx, Id pred);
|
||||||
Id EmitVoteEqual(EmitContext& ctx, Id pred);
|
Id EmitVoteEqual(EmitContext& ctx, Id pred);
|
||||||
|
|
|
@ -170,7 +170,7 @@ Id EmitCompositeConstructArrayU32x2(EmitContext& ctx, IR::Inst* inst, Id e1, Id
|
||||||
return ctx.ConstantComposite(ctx.array_U32x2, e1, e2, e3, e4);
|
return ctx.ConstantComposite(ctx.array_U32x2, e1, e2, e3, e4);
|
||||||
}
|
}
|
||||||
if (ctx.profile.support_variadic_ptp) {
|
if (ctx.profile.support_variadic_ptp) {
|
||||||
return OpCompositeConstruct(ctx.array_U32x2, e1, e2, e3, e4);
|
return ctx.OpCompositeConstruct(ctx.array_U32x2, e1, e2, e3, e4);
|
||||||
}
|
}
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
|
|
|
@ -39,6 +39,18 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
explicit ImageOperands([[maybe_unused]] EmitContext& ctx, Id offset, Id lod, Id ms) {
|
||||||
|
if (Sirit::ValidId(lod)) {
|
||||||
|
Add(spv::ImageOperandsMask::Lod, lod);
|
||||||
|
}
|
||||||
|
if (Sirit::ValidId(offset)) {
|
||||||
|
Add(spv::ImageOperandsMask::Offset, offset);
|
||||||
|
}
|
||||||
|
if (Sirit::ValidId(ms)) {
|
||||||
|
Add(spv::ImageOperandsMask::Sample, ms);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Add(spv::ImageOperandsMask new_mask, Id value) {
|
void Add(spv::ImageOperandsMask new_mask, Id value) {
|
||||||
mask = static_cast<spv::ImageOperandsMask>(static_cast<unsigned>(mask) |
|
mask = static_cast<spv::ImageOperandsMask>(static_cast<unsigned>(mask) |
|
||||||
static_cast<unsigned>(new_mask));
|
static_cast<unsigned>(new_mask));
|
||||||
|
@ -115,6 +127,10 @@ Id EmitBindlessImageGatherDref(EmitContext&) {
|
||||||
throw LogicError("Unreachable instruction");
|
throw LogicError("Unreachable instruction");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Id EmitBindlessImageFetch(EmitContext&) {
|
||||||
|
throw LogicError("Unreachable instruction");
|
||||||
|
}
|
||||||
|
|
||||||
Id EmitBoundImageSampleImplicitLod(EmitContext&) {
|
Id EmitBoundImageSampleImplicitLod(EmitContext&) {
|
||||||
throw LogicError("Unreachable instruction");
|
throw LogicError("Unreachable instruction");
|
||||||
}
|
}
|
||||||
|
@ -139,6 +155,10 @@ Id EmitBoundImageGatherDref(EmitContext&) {
|
||||||
throw LogicError("Unreachable instruction");
|
throw LogicError("Unreachable instruction");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Id EmitBoundImageFetch(EmitContext&) {
|
||||||
|
throw LogicError("Unreachable instruction");
|
||||||
|
}
|
||||||
|
|
||||||
Id EmitImageSampleImplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
Id EmitImageSampleImplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
||||||
Id bias_lc, Id offset) {
|
Id bias_lc, Id offset) {
|
||||||
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
||||||
|
@ -178,7 +198,7 @@ Id EmitImageSampleDrefExplicitLod(EmitContext& ctx, IR::Inst* inst, const IR::Va
|
||||||
}
|
}
|
||||||
|
|
||||||
Id EmitImageGather(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords, Id offset,
|
Id EmitImageGather(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords, Id offset,
|
||||||
[[maybe_unused]] Id offset2) {
|
Id offset2) {
|
||||||
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
||||||
const ImageOperands operands(ctx, offset, offset2);
|
const ImageOperands operands(ctx, offset, offset2);
|
||||||
return Emit(&EmitContext::OpImageSparseGather, &EmitContext::OpImageGather, ctx, inst,
|
return Emit(&EmitContext::OpImageSparseGather, &EmitContext::OpImageGather, ctx, inst,
|
||||||
|
@ -188,11 +208,19 @@ Id EmitImageGather(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id
|
||||||
}
|
}
|
||||||
|
|
||||||
Id EmitImageGatherDref(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
Id EmitImageGatherDref(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords,
|
||||||
Id offset, [[maybe_unused]] Id offset2, Id dref) {
|
Id offset, Id offset2, Id dref) {
|
||||||
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
||||||
const ImageOperands operands(ctx, offset, offset2);
|
const ImageOperands operands(ctx, offset, offset2);
|
||||||
return Emit(&EmitContext::OpImageSparseDrefGather, &EmitContext::OpImageDrefGather, ctx, inst,
|
return Emit(&EmitContext::OpImageSparseDrefGather, &EmitContext::OpImageDrefGather, ctx, inst,
|
||||||
ctx.F32[4], Texture(ctx, index), coords, dref, operands.Mask(), operands.Span());
|
ctx.F32[4], Texture(ctx, index), coords, dref, operands.Mask(), operands.Span());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Id EmitImageFetch(EmitContext& ctx, IR::Inst* inst, const IR::Value& index, Id coords, Id offset,
|
||||||
|
Id lod, Id ms) {
|
||||||
|
const auto info{inst->Flags<IR::TextureInstInfo>()};
|
||||||
|
const ImageOperands operands(ctx, offset, lod, ms);
|
||||||
|
return Emit(&EmitContext::OpImageSparseFetch, &EmitContext::OpImageFetch, ctx, inst, ctx.F32[4],
|
||||||
|
Texture(ctx, index), coords, operands.Mask(), operands.Span());
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace Shader::Backend::SPIRV
|
} // namespace Shader::Backend::SPIRV
|
||||||
|
|
|
@ -1491,6 +1491,12 @@ Value IREmitter::ImageGatherDref(const Value& handle, const Value& coords, const
|
||||||
return Inst(op, Flags{info}, handle, coords, offset, offset2, dref);
|
return Inst(op, Flags{info}, handle, coords, offset, offset2, dref);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Value IREmitter::ImageFetch(const Value& handle, const Value& coords, const Value& offset,
|
||||||
|
const U32& lod, const U32& multisampling, TextureInstInfo info) {
|
||||||
|
const Opcode op{handle.IsImmediate() ? Opcode::BoundImageFetch : Opcode::BindlessImageFetch};
|
||||||
|
return Inst(op, Flags{info}, handle, coords, offset, lod, multisampling);
|
||||||
|
}
|
||||||
|
|
||||||
U1 IREmitter::VoteAll(const U1& value) {
|
U1 IREmitter::VoteAll(const U1& value) {
|
||||||
return Inst<U1>(Opcode::VoteAll, value);
|
return Inst<U1>(Opcode::VoteAll, value);
|
||||||
}
|
}
|
||||||
|
|
|
@ -243,8 +243,12 @@ public:
|
||||||
[[nodiscard]] Value ImageGather(const Value& handle, const Value& coords, const Value& offset,
|
[[nodiscard]] Value ImageGather(const Value& handle, const Value& coords, const Value& offset,
|
||||||
const Value& offset2, TextureInstInfo info);
|
const Value& offset2, TextureInstInfo info);
|
||||||
|
|
||||||
[[nodiscard]] Value ImageGatherDref(const Value& handle, const Value& coords, const Value& offset,
|
[[nodiscard]] Value ImageGatherDref(const Value& handle, const Value& coords,
|
||||||
const Value& offset2, const F32& dref, TextureInstInfo info);
|
const Value& offset, const Value& offset2, const F32& dref,
|
||||||
|
TextureInstInfo info);
|
||||||
|
|
||||||
|
[[nodiscard]] Value ImageFetch(const Value& handle, const Value& coords, const Value& offset,
|
||||||
|
const U32& lod, const U32& multisampling, TextureInstInfo info);
|
||||||
|
|
||||||
[[nodiscard]] U1 VoteAll(const U1& value);
|
[[nodiscard]] U1 VoteAll(const U1& value);
|
||||||
[[nodiscard]] U1 VoteAny(const U1& value);
|
[[nodiscard]] U1 VoteAny(const U1& value);
|
||||||
|
|
|
@ -356,6 +356,7 @@ OPCODE(BindlessImageSampleDrefImplicitLod, F32, U32,
|
||||||
OPCODE(BindlessImageSampleDrefExplicitLod, F32, U32, Opaque, F32, Opaque, Opaque, )
|
OPCODE(BindlessImageSampleDrefExplicitLod, F32, U32, Opaque, F32, Opaque, Opaque, )
|
||||||
OPCODE(BindlessImageGather, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(BindlessImageGather, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
OPCODE(BindlessImageGatherDref, F32x4, U32, Opaque, Opaque, Opaque, F32, )
|
OPCODE(BindlessImageGatherDref, F32x4, U32, Opaque, Opaque, Opaque, F32, )
|
||||||
|
OPCODE(BindlessImageFetch, F32x4, U32, Opaque, U32, U32, )
|
||||||
|
|
||||||
OPCODE(BoundImageSampleImplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(BoundImageSampleImplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
OPCODE(BoundImageSampleExplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(BoundImageSampleExplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
|
@ -363,6 +364,7 @@ OPCODE(BoundImageSampleDrefImplicitLod, F32, U32,
|
||||||
OPCODE(BoundImageSampleDrefExplicitLod, F32, U32, Opaque, F32, Opaque, Opaque, )
|
OPCODE(BoundImageSampleDrefExplicitLod, F32, U32, Opaque, F32, Opaque, Opaque, )
|
||||||
OPCODE(BoundImageGather, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(BoundImageGather, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
OPCODE(BoundImageGatherDref, F32x4, U32, Opaque, Opaque, Opaque, F32, )
|
OPCODE(BoundImageGatherDref, F32x4, U32, Opaque, Opaque, Opaque, F32, )
|
||||||
|
OPCODE(BoundImageFetch, F32x4, U32, Opaque, U32, U32, )
|
||||||
|
|
||||||
OPCODE(ImageSampleImplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(ImageSampleImplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
OPCODE(ImageSampleExplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(ImageSampleExplicitLod, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
|
@ -370,6 +372,7 @@ OPCODE(ImageSampleDrefImplicitLod, F32, U32,
|
||||||
OPCODE(ImageSampleDrefExplicitLod, F32, U32, Opaque, F32, Opaque, Opaque, )
|
OPCODE(ImageSampleDrefExplicitLod, F32, U32, Opaque, F32, Opaque, Opaque, )
|
||||||
OPCODE(ImageGather, F32x4, U32, Opaque, Opaque, Opaque, )
|
OPCODE(ImageGather, F32x4, U32, Opaque, Opaque, Opaque, )
|
||||||
OPCODE(ImageGatherDref, F32x4, U32, Opaque, Opaque, Opaque, F32, )
|
OPCODE(ImageGatherDref, F32x4, U32, Opaque, Opaque, Opaque, F32, )
|
||||||
|
OPCODE(ImageFetch, F32x4, U32, Opaque, U32, U32, )
|
||||||
|
|
||||||
// Warp operations
|
// Warp operations
|
||||||
OPCODE(VoteAll, U1, U1, )
|
OPCODE(VoteAll, U1, U1, )
|
||||||
|
|
|
@ -51,6 +51,9 @@ IR::Opcode IndexedInstruction(const IR::Inst& inst) {
|
||||||
case IR::Opcode::BindlessImageGatherDref:
|
case IR::Opcode::BindlessImageGatherDref:
|
||||||
case IR::Opcode::BoundImageGatherDref:
|
case IR::Opcode::BoundImageGatherDref:
|
||||||
return IR::Opcode::ImageGatherDref;
|
return IR::Opcode::ImageGatherDref;
|
||||||
|
case IR::Opcode::BindlessImageFetch:
|
||||||
|
case IR::Opcode::BoundImageFetch:
|
||||||
|
return IR::Opcode::ImageFetch;
|
||||||
default:
|
default:
|
||||||
return IR::Opcode::Void;
|
return IR::Opcode::Void;
|
||||||
}
|
}
|
||||||
|
@ -64,6 +67,7 @@ bool IsBindless(const IR::Inst& inst) {
|
||||||
case IR::Opcode::BindlessImageSampleDrefExplicitLod:
|
case IR::Opcode::BindlessImageSampleDrefExplicitLod:
|
||||||
case IR::Opcode::BindlessImageGather:
|
case IR::Opcode::BindlessImageGather:
|
||||||
case IR::Opcode::BindlessImageGatherDref:
|
case IR::Opcode::BindlessImageGatherDref:
|
||||||
|
case IR::Opcode::BindlessImageFetch:
|
||||||
return true;
|
return true;
|
||||||
case IR::Opcode::BoundImageSampleImplicitLod:
|
case IR::Opcode::BoundImageSampleImplicitLod:
|
||||||
case IR::Opcode::BoundImageSampleExplicitLod:
|
case IR::Opcode::BoundImageSampleExplicitLod:
|
||||||
|
@ -71,6 +75,7 @@ bool IsBindless(const IR::Inst& inst) {
|
||||||
case IR::Opcode::BoundImageSampleDrefExplicitLod:
|
case IR::Opcode::BoundImageSampleDrefExplicitLod:
|
||||||
case IR::Opcode::BoundImageGather:
|
case IR::Opcode::BoundImageGather:
|
||||||
case IR::Opcode::BoundImageGatherDref:
|
case IR::Opcode::BoundImageGatherDref:
|
||||||
|
case IR::Opcode::BoundImageFetch:
|
||||||
return false;
|
return false;
|
||||||
default:
|
default:
|
||||||
throw InvalidArgument("Invalid opcode {}", inst.Opcode());
|
throw InvalidArgument("Invalid opcode {}", inst.Opcode());
|
||||||
|
|
Reference in New Issue