mirror of
https://github.com/KhronosGroup/SPIRV-Tools
synced 2024-10-18 11:10:05 +00:00
instrument: Reduce number of inst_bindless_stream_write_6 calls (#5327)
Multiple calls to this function were causing vkCreateGraphicsPipelines to be 3x slower on some driver. I suspect this was because each call had to be inlined separately which bloated the code and caused more work in the driver's SPIRV -> native instruction compilation.
This commit is contained in:
parent
02cd71d41c
commit
47fff21d52
@ -132,50 +132,58 @@ void InstBindlessCheckPass::SetupInputBufferIds() {
|
|||||||
|
|
||||||
// clang-format off
|
// clang-format off
|
||||||
// GLSL:
|
// GLSL:
|
||||||
//bool inst_bindless_check_desc(uint shader_id, uint line, uvec4 stage_info, uint desc_set_idx, uint binding_idx, uint desc_idx,
|
//bool inst_bindless_check_desc(uint shader_id, uint inst_num, uvec4 stage_info, uint desc_set, uint binding, uint desc_index,
|
||||||
// uint offset)
|
// uint byte_offset)
|
||||||
//{
|
//{
|
||||||
// if (desc_set_idx >= inst_bindless_input_buffer.desc_sets.length()) {
|
// uint error = 0u;
|
||||||
// // kInstErrorBindlessBounds
|
// uint param5 = 0u;
|
||||||
// inst_bindless_stream_write_6(shader_id, line, stage_info, 1, desc_set_idx, binding_idx, desc_idx, 0, 0);
|
// uint param6 = 0u;
|
||||||
// return false;
|
// uint num_bindings = 0u;
|
||||||
|
// uint init_state = 0u;
|
||||||
|
// if (desc_set >= 32u) {
|
||||||
|
// error = 1u;
|
||||||
// }
|
// }
|
||||||
// DescriptorSetData set_data = inst_bindless_input_buffer.desc_sets[desc_set_idx];
|
// inst_bindless_DescriptorSetData set_data;
|
||||||
// uvec2 ptr_vec = uvec2(set_data);
|
// if (error == 0u) {
|
||||||
// if (ptr_vec.x == 0 && ptr_vec.y == 0) {
|
// set_data = inst_bindless_input_buffer.desc_sets[desc_set];
|
||||||
// // kInstErrorBindlessBounds
|
// uvec2 ptr_vec = uvec2(set_data);
|
||||||
// inst_bindless_stream_write_6(shader_id, line, stage_info, 1, desc_set_idx, binding_idx, desc_idx, 0, 0);
|
// if ((ptr_vec.x == 0u) && (ptr_vec.y == 0u)) {
|
||||||
// return false;
|
// error = 1u;
|
||||||
|
// }
|
||||||
// }
|
// }
|
||||||
// uint num_bindings = set_data.num_bindings;
|
// if (error == 0u) {
|
||||||
// if (binding_idx >= num_bindings) {
|
// num_bindings = set_data.num_bindings;
|
||||||
// // kInstErrorBindlessBounds
|
// if (binding >= num_bindings) {
|
||||||
// inst_bindless_stream_write_6(shader_id, line, stage_info, 1, desc_set_idx, binding_idx, desc_idx, 0, 0);
|
// error = 1u;
|
||||||
// return false;
|
// }
|
||||||
// }
|
// }
|
||||||
// uint binding_length = set_data.data[binding_idx];
|
// if (error == 0u) {
|
||||||
// if (desc_idx >= binding_length) {
|
// if (desc_index >= set_data.data[binding]) {
|
||||||
// // kInstErrorBindlessBounds
|
// error = 1u;
|
||||||
// inst_bindless_stream_write_6(shader_id, line, stage_info, 1, desc_set_idx, binding_idx, desc_idx, binding_length, 0);
|
// param5 = set_data.data[binding];
|
||||||
// return false;
|
// }
|
||||||
// }
|
// }
|
||||||
// uint desc_records_start = set_data.data[num_bindings + binding_idx];
|
// if (0u == error) {
|
||||||
// uint init_or_len = set_data.data[desc_records_start + desc_idx];
|
// uint state_index = set_data.data[num_bindings + binding] + desc_index;
|
||||||
// if (init_or_len == 0) {
|
// init_state = set_data.data[state_index];
|
||||||
// // kInstErrorBindlessUninit
|
// if (init_state == 0u) {
|
||||||
// inst_bindless_stream_write_6(shader_id, line, stage_info, 2, desc_set_idx, binding_idx, desc_idx, 0, 0);
|
// error = 2u;
|
||||||
// return false;
|
// }
|
||||||
// }
|
// }
|
||||||
// if (offset >= init_or_len) {
|
// if (error == 0u) {
|
||||||
// // kInstErrorOOB
|
// if (byte_offset >= init_state) {
|
||||||
// inst_bindless_stream_write_6(shader_id, line, stage_info, 4, desc_set_idx, binding_idx, desc_idx, offset,
|
// error = 4u;
|
||||||
// init_or_len);
|
// param5 = byte_offset;
|
||||||
|
// param6 = init_state;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// if (0u != error) {
|
||||||
|
// inst_bindless_stream_write_6(shader_id, inst_num, stage_info, error, desc_set, binding, desc_index, param5, param6);
|
||||||
// return false;
|
// return false;
|
||||||
// }
|
// }
|
||||||
// return true;
|
// return true;
|
||||||
//}
|
//}
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
uint32_t InstBindlessCheckPass::GenDescCheckFunctionId() {
|
uint32_t InstBindlessCheckPass::GenDescCheckFunctionId() {
|
||||||
enum {
|
enum {
|
||||||
kShaderId = 0,
|
kShaderId = 0,
|
||||||
@ -205,235 +213,427 @@ uint32_t InstBindlessCheckPass::GenDescCheckFunctionId() {
|
|||||||
|
|
||||||
const std::vector<uint32_t> param_ids = AddParameters(*func, param_types);
|
const std::vector<uint32_t> param_ids = AddParameters(*func, param_types);
|
||||||
|
|
||||||
|
const uint32_t func_uint_ptr =
|
||||||
|
type_mgr->FindPointerToType(GetUintId(), spv::StorageClass::Function);
|
||||||
// Create block
|
// Create block
|
||||||
auto new_blk_ptr = MakeUnique<BasicBlock>(NewLabel(TakeNextId()));
|
auto new_blk_ptr = MakeUnique<BasicBlock>(NewLabel(TakeNextId()));
|
||||||
InstructionBuilder builder(
|
InstructionBuilder builder(
|
||||||
context(), new_blk_ptr.get(),
|
context(), new_blk_ptr.get(),
|
||||||
IRContext::kAnalysisDefUse | IRContext::kAnalysisInstrToBlockMapping);
|
IRContext::kAnalysisDefUse | IRContext::kAnalysisInstrToBlockMapping);
|
||||||
|
Instruction* inst;
|
||||||
|
const uint32_t zero_id = builder.GetUintConstantId(0);
|
||||||
const uint32_t false_id = builder.GetBoolConstantId(false);
|
const uint32_t false_id = builder.GetBoolConstantId(false);
|
||||||
const uint32_t true_id = builder.GetBoolConstantId(true);
|
const uint32_t true_id = builder.GetBoolConstantId(true);
|
||||||
Instruction* inst;
|
const uint32_t uint_ptr = type_mgr->FindPointerToType(
|
||||||
|
GetUintId(), spv::StorageClass::PhysicalStorageBuffer);
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(func_uint_ptr, spv::Op::OpVariable,
|
||||||
|
uint32_t(spv::StorageClass::Function), zero_id);
|
||||||
|
const uint32_t error_var = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(func_uint_ptr, spv::Op::OpVariable,
|
||||||
|
uint32_t(spv::StorageClass::Function), zero_id);
|
||||||
|
const uint32_t param5_var = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(func_uint_ptr, spv::Op::OpVariable,
|
||||||
|
uint32_t(spv::StorageClass::Function), zero_id);
|
||||||
|
const uint32_t param6_var = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(func_uint_ptr, spv::Op::OpVariable,
|
||||||
|
uint32_t(spv::StorageClass::Function), zero_id);
|
||||||
|
const uint32_t num_bindings_var = inst->result_id();
|
||||||
|
inst = builder.AddBinaryOp(func_uint_ptr, spv::Op::OpVariable,
|
||||||
|
uint32_t(spv::StorageClass::Function), zero_id);
|
||||||
|
const uint32_t init_status_var = inst->result_id();
|
||||||
|
|
||||||
|
const uint32_t desc_set_ptr_ptr = type_mgr->FindPointerToType(
|
||||||
|
desc_set_ptr_id_, spv::StorageClass::Function);
|
||||||
|
|
||||||
|
inst = builder.AddUnaryOp(desc_set_ptr_ptr, spv::Op::OpVariable,
|
||||||
|
uint32_t(spv::StorageClass::Function));
|
||||||
|
const uint32_t desc_set_ptr_var = inst->result_id();
|
||||||
|
get_decoration_mgr()->AddDecoration(
|
||||||
|
desc_set_ptr_var, uint32_t(spv::Decoration::AliasedPointer));
|
||||||
|
|
||||||
|
uint32_t check_label_id = TakeNextId();
|
||||||
|
auto check_label = NewLabel(check_label_id);
|
||||||
|
uint32_t skip_label_id = TakeNextId();
|
||||||
|
auto skip_label = NewLabel(skip_label_id);
|
||||||
inst = builder.AddBinaryOp(
|
inst = builder.AddBinaryOp(
|
||||||
GetBoolId(), spv::Op::OpUGreaterThanEqual, param_ids[kDescSet],
|
GetBoolId(), spv::Op::OpUGreaterThanEqual, param_ids[kDescSet],
|
||||||
builder.GetUintConstantId(kDebugInputBindlessMaxDescSets));
|
builder.GetUintConstantId(kDebugInputBindlessMaxDescSets));
|
||||||
const uint32_t desc_cmp_id = inst->result_id();
|
const uint32_t desc_cmp_id = inst->result_id();
|
||||||
|
|
||||||
uint32_t error_blk_id = TakeNextId();
|
(void)builder.AddConditionalBranch(desc_cmp_id, check_label_id, skip_label_id,
|
||||||
uint32_t merge_blk_id = TakeNextId();
|
skip_label_id);
|
||||||
std::unique_ptr<Instruction> merge_label(NewLabel(merge_blk_id));
|
|
||||||
std::unique_ptr<Instruction> error_label(NewLabel(error_blk_id));
|
|
||||||
(void)builder.AddConditionalBranch(desc_cmp_id, error_blk_id, merge_blk_id,
|
|
||||||
merge_blk_id);
|
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
// error return
|
// set error
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(check_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
builder.AddStore(error_var,
|
||||||
|
builder.GetUintConstantId(kInstErrorBindlessBounds));
|
||||||
|
builder.AddBranch(skip_label_id);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
// check descriptor set table entry is non-null
|
// check descriptor set table entry is non-null
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(skip_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
|
||||||
const uint32_t desc_set_ptr_ptr = type_mgr->FindPointerToType(
|
check_label_id = TakeNextId();
|
||||||
desc_set_ptr_id_, spv::StorageClass::StorageBuffer);
|
check_label = NewLabel(check_label_id);
|
||||||
|
skip_label_id = TakeNextId();
|
||||||
|
skip_label = NewLabel(skip_label_id);
|
||||||
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
|
uint32_t error_val_id = inst->result_id();
|
||||||
|
|
||||||
inst = builder.AddAccessChain(
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, error_val_id,
|
||||||
desc_set_ptr_ptr, input_buffer_id_,
|
zero_id);
|
||||||
{builder.GetUintConstantId(0), param_ids[kDescSet]});
|
uint32_t no_error_id = inst->result_id();
|
||||||
const uint32_t set_access_chain_id = inst->result_id();
|
(void)builder.AddConditionalBranch(no_error_id, check_label_id, skip_label_id,
|
||||||
|
skip_label_id);
|
||||||
inst = builder.AddLoad(desc_set_ptr_id_, set_access_chain_id);
|
|
||||||
const uint32_t desc_set_ptr_id = inst->result_id();
|
|
||||||
|
|
||||||
inst =
|
|
||||||
builder.AddUnaryOp(GetVecUintId(2), spv::Op::OpBitcast, desc_set_ptr_id);
|
|
||||||
const uint32_t ptr_as_uvec_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddCompositeExtract(GetUintId(), ptr_as_uvec_id, {0});
|
|
||||||
const uint32_t uvec_x = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, uvec_x,
|
|
||||||
builder.GetUintConstantId(0));
|
|
||||||
const uint32_t x_is_zero_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddCompositeExtract(GetUintId(), ptr_as_uvec_id, {1});
|
|
||||||
const uint32_t uvec_y = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, uvec_y,
|
|
||||||
builder.GetUintConstantId(0));
|
|
||||||
const uint32_t y_is_zero_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpLogicalAnd, x_is_zero_id,
|
|
||||||
y_is_zero_id);
|
|
||||||
const uint32_t is_null_id = inst->result_id();
|
|
||||||
|
|
||||||
error_blk_id = TakeNextId();
|
|
||||||
merge_blk_id = TakeNextId();
|
|
||||||
merge_label = NewLabel(merge_blk_id);
|
|
||||||
error_label = NewLabel(error_blk_id);
|
|
||||||
(void)builder.AddConditionalBranch(is_null_id, error_blk_id, merge_blk_id,
|
|
||||||
merge_blk_id);
|
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
// error return
|
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(check_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
GenDebugStreamWrite(
|
|
||||||
param_ids[kShaderId], param_ids[kInstructionIndex], param_ids[kStageInfo],
|
{
|
||||||
{builder.GetUintConstantId(kInstErrorBindlessBounds), param_ids[kDescSet],
|
const uint32_t desc_set_ptr_ptr_sb = type_mgr->FindPointerToType(
|
||||||
param_ids[kDescBinding], param_ids[kDescIndex],
|
desc_set_ptr_id_, spv::StorageClass::StorageBuffer);
|
||||||
builder.GetUintConstantId(0), builder.GetUintConstantId(0)},
|
|
||||||
&builder);
|
inst = builder.AddAccessChain(desc_set_ptr_ptr_sb, input_buffer_id_,
|
||||||
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
{zero_id, param_ids[kDescSet]});
|
||||||
|
const uint32_t set_access_chain_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddLoad(desc_set_ptr_id_, set_access_chain_id);
|
||||||
|
const uint32_t desc_set_ptr_id = inst->result_id();
|
||||||
|
|
||||||
|
builder.AddStore(desc_set_ptr_var, desc_set_ptr_id);
|
||||||
|
|
||||||
|
inst = builder.AddUnaryOp(GetVecUintId(2), spv::Op::OpBitcast,
|
||||||
|
desc_set_ptr_id);
|
||||||
|
const uint32_t ptr_as_uvec_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddCompositeExtract(GetUintId(), ptr_as_uvec_id, {0});
|
||||||
|
const uint32_t uvec_x = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, uvec_x, zero_id);
|
||||||
|
const uint32_t x_is_zero_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddCompositeExtract(GetUintId(), ptr_as_uvec_id, {1});
|
||||||
|
const uint32_t uvec_y = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, uvec_y, zero_id);
|
||||||
|
const uint32_t y_is_zero_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpLogicalAnd, x_is_zero_id,
|
||||||
|
y_is_zero_id);
|
||||||
|
const uint32_t is_null_id = inst->result_id();
|
||||||
|
|
||||||
|
const uint32_t error_label_id = TakeNextId();
|
||||||
|
auto error_label = NewLabel(error_label_id);
|
||||||
|
const uint32_t merge_label_id = TakeNextId();
|
||||||
|
auto merge_label = NewLabel(merge_label_id);
|
||||||
|
(void)builder.AddConditionalBranch(is_null_id, error_label_id,
|
||||||
|
merge_label_id, merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
// set error
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddStore(error_var,
|
||||||
|
builder.GetUintConstantId(kInstErrorBindlessBounds));
|
||||||
|
builder.AddBranch(merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddBranch(skip_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
}
|
||||||
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(skip_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
|
||||||
|
check_label_id = TakeNextId();
|
||||||
|
check_label = NewLabel(check_label_id);
|
||||||
|
skip_label_id = TakeNextId();
|
||||||
|
skip_label = NewLabel(skip_label_id);
|
||||||
|
|
||||||
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
|
error_val_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, error_val_id,
|
||||||
|
zero_id);
|
||||||
|
no_error_id = inst->result_id();
|
||||||
|
(void)builder.AddConditionalBranch(no_error_id, check_label_id, skip_label_id,
|
||||||
|
skip_label_id);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
// check binding is in range
|
// check binding is in range
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(check_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
{
|
||||||
|
inst = builder.AddLoad(desc_set_ptr_id_, desc_set_ptr_var);
|
||||||
|
const uint32_t desc_set_ptr_id = inst->result_id();
|
||||||
|
|
||||||
const uint32_t uint_ptr = type_mgr->FindPointerToType(
|
inst = builder.AddAccessChain(uint_ptr, desc_set_ptr_id, {zero_id});
|
||||||
GetUintId(), spv::StorageClass::PhysicalStorageBuffer);
|
const uint32_t binding_access_chain_id = inst->result_id();
|
||||||
|
|
||||||
inst = builder.AddAccessChain(uint_ptr, desc_set_ptr_id,
|
inst = builder.AddLoad(GetUintId(), binding_access_chain_id, 8);
|
||||||
{builder.GetUintConstantId(0)});
|
const uint32_t num_bindings_id = inst->result_id();
|
||||||
const uint32_t binding_access_chain_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddLoad(GetUintId(), binding_access_chain_id, 8);
|
builder.AddStore(num_bindings_var, num_bindings_id);
|
||||||
const uint32_t num_bindings_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpUGreaterThanEqual,
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpUGreaterThanEqual,
|
||||||
param_ids[kDescBinding], num_bindings_id);
|
param_ids[kDescBinding], num_bindings_id);
|
||||||
const uint32_t bindings_cmp_id = inst->result_id();
|
const uint32_t bindings_cmp_id = inst->result_id();
|
||||||
|
|
||||||
error_blk_id = TakeNextId();
|
const uint32_t error_label_id = TakeNextId();
|
||||||
merge_blk_id = TakeNextId();
|
auto error_label = NewLabel(error_label_id);
|
||||||
merge_label = NewLabel(merge_blk_id);
|
const uint32_t merge_label_id = TakeNextId();
|
||||||
error_label = NewLabel(error_blk_id);
|
auto merge_label = NewLabel(merge_label_id);
|
||||||
(void)builder.AddConditionalBranch(bindings_cmp_id, error_blk_id,
|
(void)builder.AddConditionalBranch(bindings_cmp_id, error_label_id,
|
||||||
merge_blk_id, merge_blk_id);
|
merge_label_id, merge_label_id);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
// error return
|
// set error
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
GenDebugStreamWrite(
|
builder.AddStore(error_var,
|
||||||
param_ids[kShaderId], param_ids[kInstructionIndex], param_ids[kStageInfo],
|
builder.GetUintConstantId(kInstErrorBindlessBounds));
|
||||||
{builder.GetUintConstantId(kInstErrorBindlessBounds), param_ids[kDescSet],
|
builder.AddBranch(merge_label_id);
|
||||||
param_ids[kDescBinding], param_ids[kDescIndex],
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
builder.GetUintConstantId(0), builder.GetUintConstantId(0)},
|
|
||||||
&builder);
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
||||||
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
builder.AddBranch(skip_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
}
|
||||||
|
|
||||||
// read binding length
|
// read binding length
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(skip_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
|
||||||
inst = builder.AddAccessChain(
|
check_label_id = TakeNextId();
|
||||||
uint_ptr, desc_set_ptr_id,
|
check_label = NewLabel(check_label_id);
|
||||||
{{builder.GetUintConstantId(1), param_ids[kDescBinding]}});
|
skip_label_id = TakeNextId();
|
||||||
const uint32_t length_ac_id = inst->result_id();
|
skip_label = NewLabel(skip_label_id);
|
||||||
|
|
||||||
inst = builder.AddLoad(GetUintId(), length_ac_id, sizeof(uint32_t));
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
const uint32_t length_id = inst->result_id();
|
error_val_id = inst->result_id();
|
||||||
|
|
||||||
// Check descriptor index in bounds
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, error_val_id,
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpUGreaterThanEqual,
|
zero_id);
|
||||||
param_ids[kDescIndex], length_id);
|
no_error_id = inst->result_id();
|
||||||
const uint32_t desc_idx_range_id = inst->result_id();
|
(void)builder.AddConditionalBranch(no_error_id, check_label_id, skip_label_id,
|
||||||
|
skip_label_id);
|
||||||
error_blk_id = TakeNextId();
|
|
||||||
merge_blk_id = TakeNextId();
|
|
||||||
merge_label = NewLabel(merge_blk_id);
|
|
||||||
error_label = NewLabel(error_blk_id);
|
|
||||||
(void)builder.AddConditionalBranch(desc_idx_range_id, error_blk_id,
|
|
||||||
merge_blk_id, merge_blk_id);
|
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
// Error return
|
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(check_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
GenDebugStreamWrite(
|
{
|
||||||
param_ids[kShaderId], param_ids[kInstructionIndex], param_ids[kStageInfo],
|
inst = builder.AddLoad(desc_set_ptr_id_, desc_set_ptr_var);
|
||||||
{builder.GetUintConstantId(kInstErrorBindlessBounds), param_ids[kDescSet],
|
const uint32_t desc_set_ptr_id = inst->result_id();
|
||||||
param_ids[kDescBinding], param_ids[kDescIndex], length_id,
|
|
||||||
builder.GetUintConstantId(0)},
|
inst = builder.AddAccessChain(
|
||||||
&builder);
|
uint_ptr, desc_set_ptr_id,
|
||||||
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
{{builder.GetUintConstantId(1), param_ids[kDescBinding]}});
|
||||||
|
const uint32_t length_ac_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddLoad(GetUintId(), length_ac_id, sizeof(uint32_t));
|
||||||
|
const uint32_t length_id = inst->result_id();
|
||||||
|
|
||||||
|
// Check descriptor index in bounds
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpUGreaterThanEqual,
|
||||||
|
param_ids[kDescIndex], length_id);
|
||||||
|
const uint32_t desc_idx_range_id = inst->result_id();
|
||||||
|
|
||||||
|
const uint32_t error_label_id = TakeNextId();
|
||||||
|
auto error_label = NewLabel(error_label_id);
|
||||||
|
const uint32_t merge_label_id = TakeNextId();
|
||||||
|
auto merge_label = NewLabel(merge_label_id);
|
||||||
|
(void)builder.AddConditionalBranch(desc_idx_range_id, error_label_id,
|
||||||
|
merge_label_id, merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
// set error
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddStore(error_var,
|
||||||
|
builder.GetUintConstantId(kInstErrorBindlessBounds));
|
||||||
|
builder.AddStore(param5_var, length_id);
|
||||||
|
builder.AddBranch(merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddBranch(skip_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
}
|
||||||
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(skip_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
|
error_val_id = inst->result_id();
|
||||||
|
|
||||||
|
check_label_id = TakeNextId();
|
||||||
|
check_label = NewLabel(check_label_id);
|
||||||
|
skip_label_id = TakeNextId();
|
||||||
|
skip_label = NewLabel(skip_label_id);
|
||||||
|
|
||||||
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
|
error_val_id = inst->result_id();
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, zero_id,
|
||||||
|
error_val_id);
|
||||||
|
no_error_id = inst->result_id();
|
||||||
|
|
||||||
|
(void)builder.AddConditionalBranch(no_error_id, check_label_id, skip_label_id,
|
||||||
|
skip_label_id);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
// Read descriptor init status
|
// Read descriptor init status
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(check_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
{
|
||||||
|
inst = builder.AddLoad(desc_set_ptr_id_, desc_set_ptr_var);
|
||||||
|
const uint32_t desc_set_ptr_id = inst->result_id();
|
||||||
|
|
||||||
inst = builder.AddIAdd(GetUintId(), num_bindings_id, param_ids[kDescBinding]);
|
inst = builder.AddLoad(GetUintId(), num_bindings_var);
|
||||||
const uint32_t state_offset_id = inst->result_id();
|
const uint32_t num_bindings_id = inst->result_id();
|
||||||
|
|
||||||
inst =
|
inst =
|
||||||
builder.AddAccessChain(uint_ptr, desc_set_ptr_id,
|
builder.AddIAdd(GetUintId(), num_bindings_id, param_ids[kDescBinding]);
|
||||||
{{builder.GetUintConstantId(1), state_offset_id}});
|
const uint32_t state_offset_id = inst->result_id();
|
||||||
const uint32_t state_start_ac_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddLoad(GetUintId(), state_start_ac_id, sizeof(uint32_t));
|
inst = builder.AddAccessChain(
|
||||||
const uint32_t state_start_id = inst->result_id();
|
uint_ptr, desc_set_ptr_id,
|
||||||
|
{{builder.GetUintConstantId(1), state_offset_id}});
|
||||||
|
const uint32_t state_start_ac_id = inst->result_id();
|
||||||
|
|
||||||
inst = builder.AddIAdd(GetUintId(), state_start_id, param_ids[kDescIndex]);
|
inst = builder.AddLoad(GetUintId(), state_start_ac_id, sizeof(uint32_t));
|
||||||
const uint32_t state_entry_id = inst->result_id();
|
const uint32_t state_start_id = inst->result_id();
|
||||||
|
|
||||||
// Note: length starts from the beginning of the buffer, not the beginning of
|
inst = builder.AddIAdd(GetUintId(), state_start_id, param_ids[kDescIndex]);
|
||||||
// the data array
|
const uint32_t state_entry_id = inst->result_id();
|
||||||
inst =
|
|
||||||
builder.AddAccessChain(uint_ptr, desc_set_ptr_id,
|
|
||||||
{{builder.GetUintConstantId(1), state_entry_id}});
|
|
||||||
const uint32_t init_ac_id = inst->result_id();
|
|
||||||
|
|
||||||
inst = builder.AddLoad(GetUintId(), init_ac_id, sizeof(uint32_t));
|
// Note: length starts from the beginning of the buffer, not the beginning
|
||||||
const uint32_t init_status_id = inst->result_id();
|
// of the data array
|
||||||
|
inst = builder.AddAccessChain(
|
||||||
|
uint_ptr, desc_set_ptr_id,
|
||||||
|
{{builder.GetUintConstantId(1), state_entry_id}});
|
||||||
|
const uint32_t init_ac_id = inst->result_id();
|
||||||
|
|
||||||
// Check for uninitialized descriptor
|
inst = builder.AddLoad(GetUintId(), init_ac_id, sizeof(uint32_t));
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, init_status_id,
|
const uint32_t init_status_id = inst->result_id();
|
||||||
builder.GetUintConstantId(0));
|
|
||||||
const uint32_t uninit_check_id = inst->result_id();
|
builder.AddStore(init_status_var, init_status_id);
|
||||||
error_blk_id = TakeNextId();
|
|
||||||
merge_blk_id = TakeNextId();
|
// Check for uninitialized descriptor
|
||||||
merge_label = NewLabel(merge_blk_id);
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, init_status_id,
|
||||||
error_label = NewLabel(error_blk_id);
|
zero_id);
|
||||||
(void)builder.AddConditionalBranch(uninit_check_id, error_blk_id,
|
const uint32_t uninit_check_id = inst->result_id();
|
||||||
merge_blk_id, merge_blk_id);
|
const uint32_t error_label_id = TakeNextId();
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
auto error_label = NewLabel(error_label_id);
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
const uint32_t merge_label_id = TakeNextId();
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
auto merge_label = NewLabel(merge_label_id);
|
||||||
GenDebugStreamWrite(
|
(void)builder.AddConditionalBranch(uninit_check_id, error_label_id,
|
||||||
param_ids[kShaderId], param_ids[kInstructionIndex], param_ids[kStageInfo],
|
merge_label_id, merge_label_id);
|
||||||
{builder.GetUintConstantId(kInstErrorBindlessUninit), param_ids[kDescSet],
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
param_ids[kDescBinding], param_ids[kDescIndex],
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
||||||
builder.GetUintConstantId(0), builder.GetUintConstantId(0)},
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
&builder);
|
builder.AddStore(error_var,
|
||||||
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
builder.GetUintConstantId(kInstErrorBindlessUninit));
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
builder.AddBranch(merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddBranch(skip_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
}
|
||||||
|
|
||||||
// Check for OOB.
|
// Check for OOB.
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(skip_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpUGreaterThanEqual,
|
|
||||||
param_ids[kByteOffset], init_status_id);
|
|
||||||
const uint32_t buf_offset_range_id = inst->result_id();
|
|
||||||
|
|
||||||
error_blk_id = TakeNextId();
|
check_label_id = TakeNextId();
|
||||||
merge_blk_id = TakeNextId();
|
check_label = NewLabel(check_label_id);
|
||||||
merge_label = NewLabel(merge_blk_id);
|
skip_label_id = TakeNextId();
|
||||||
error_label = NewLabel(error_blk_id);
|
skip_label = NewLabel(skip_label_id);
|
||||||
(void)builder.AddConditionalBranch(buf_offset_range_id, error_blk_id,
|
|
||||||
merge_blk_id, merge_blk_id);
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
|
error_val_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpIEqual, error_val_id,
|
||||||
|
zero_id);
|
||||||
|
no_error_id = inst->result_id();
|
||||||
|
(void)builder.AddConditionalBranch(no_error_id, check_label_id, skip_label_id,
|
||||||
|
skip_label_id);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
// Error return
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(check_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
{
|
||||||
|
inst = builder.AddLoad(GetUintId(), init_status_var);
|
||||||
|
const uint32_t init_status_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpUGreaterThanEqual,
|
||||||
|
param_ids[kByteOffset], init_status_id);
|
||||||
|
const uint32_t buf_offset_range_id = inst->result_id();
|
||||||
|
|
||||||
|
const uint32_t error_label_id = TakeNextId();
|
||||||
|
const uint32_t merge_label_id = TakeNextId();
|
||||||
|
auto error_label = NewLabel(error_label_id);
|
||||||
|
auto merge_label = NewLabel(merge_label_id);
|
||||||
|
(void)builder.AddConditionalBranch(buf_offset_range_id, error_label_id,
|
||||||
|
merge_label_id, merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
|
// set error
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddStore(error_var, builder.GetUintConstantId(kInstErrorOOB));
|
||||||
|
builder.AddStore(param5_var, param_ids[kByteOffset]);
|
||||||
|
builder.AddStore(param6_var, init_status_id);
|
||||||
|
builder.AddBranch(merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(merge_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
builder.AddBranch(skip_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
}
|
||||||
|
|
||||||
|
// check for error
|
||||||
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(skip_label));
|
||||||
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
inst = builder.AddLoad(GetUintId(), error_var);
|
||||||
|
error_val_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddBinaryOp(GetBoolId(), spv::Op::OpINotEqual, zero_id,
|
||||||
|
error_val_id);
|
||||||
|
const uint32_t is_error_id = inst->result_id();
|
||||||
|
|
||||||
|
const uint32_t error_label_id = TakeNextId();
|
||||||
|
auto error_label = NewLabel(error_label_id);
|
||||||
|
const uint32_t merge_label_id = TakeNextId();
|
||||||
|
auto merge_label = NewLabel(merge_label_id);
|
||||||
|
(void)builder.AddConditionalBranch(is_error_id, error_label_id,
|
||||||
|
merge_label_id, merge_label_id);
|
||||||
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
|
||||||
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
new_blk_ptr = MakeUnique<BasicBlock>(std::move(error_label));
|
||||||
builder.SetInsertPoint(&*new_blk_ptr);
|
builder.SetInsertPoint(&*new_blk_ptr);
|
||||||
|
|
||||||
|
// error output
|
||||||
|
inst = builder.AddLoad(GetUintId(), param5_var);
|
||||||
|
const uint32_t param5_val_id = inst->result_id();
|
||||||
|
|
||||||
|
inst = builder.AddLoad(GetUintId(), param6_var);
|
||||||
|
const uint32_t param6_val_id = inst->result_id();
|
||||||
|
|
||||||
GenDebugStreamWrite(
|
GenDebugStreamWrite(
|
||||||
param_ids[kShaderId], param_ids[kInstructionIndex], param_ids[kStageInfo],
|
param_ids[kShaderId], param_ids[kInstructionIndex], param_ids[kStageInfo],
|
||||||
{builder.GetUintConstantId(kInstErrorOOB), param_ids[kDescSet],
|
{error_val_id, param_ids[kDescSet], param_ids[kDescBinding],
|
||||||
param_ids[kDescBinding], param_ids[kDescIndex], param_ids[kByteOffset],
|
param_ids[kDescIndex], param5_val_id, param6_val_id},
|
||||||
init_status_id},
|
|
||||||
&builder);
|
&builder);
|
||||||
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
(void)builder.AddUnaryOp(0, spv::Op::OpReturnValue, false_id);
|
||||||
func->AddBasicBlock(std::move(new_blk_ptr));
|
func->AddBasicBlock(std::move(new_blk_ptr));
|
||||||
|
@ -135,19 +135,32 @@ static const std::string kCheckDesc = R"(
|
|||||||
; CHECK: [[di_shader_id:%\w+]] = OpFunctionParameter %uint
|
; CHECK: [[di_shader_id:%\w+]] = OpFunctionParameter %uint
|
||||||
; CHECK: [[di_line:%\w+]] = OpFunctionParameter %uint
|
; CHECK: [[di_line:%\w+]] = OpFunctionParameter %uint
|
||||||
; CHECK: [[di_stage_info:%\w+]] = OpFunctionParameter %v4uint
|
; CHECK: [[di_stage_info:%\w+]] = OpFunctionParameter %v4uint
|
||||||
; CHECK: [[di_desc_set_idx:%\w+]] = OpFunctionParameter %uint
|
; CHECK: [[di_desc_set:%\w+]] = OpFunctionParameter %uint
|
||||||
; CHECK: [[di_binding_idx:%\w+]] = OpFunctionParameter %uint
|
; CHECK: [[di_binding:%\w+]] = OpFunctionParameter %uint
|
||||||
; CHECK: [[di_desc_idx:%\w+]] = OpFunctionParameter %uint
|
; CHECK: [[di_desc_idx:%\w+]] = OpFunctionParameter %uint
|
||||||
; CHECK: [[di_byte_offset:%\w+]] = OpFunctionParameter %uint
|
; CHECK: [[di_byte_offset:%\w+]] = OpFunctionParameter %uint
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_desc_set_idx]] %uint_32
|
; CHECK: [[di_error:%\w+]] = OpVariable %_ptr_Function_uint Function %uint_0
|
||||||
|
; CHECK: [[di_param5:%\w+]] = OpVariable %_ptr_Function_uint Function %uint_0
|
||||||
|
; CHECK: [[di_param6:%\w+]] = OpVariable %_ptr_Function_uint Function %uint_0
|
||||||
|
; CHECK: [[di_num_bindings:%\w+]] = OpVariable %_ptr_Function_uint Function %uint_0
|
||||||
|
; CHECK: [[di_init_status:%\w+]] = OpVariable %_ptr_Function_uint Function %uint_0
|
||||||
|
; CHECK: [[di_desc_set_ptr:%\w+]] = OpVariable %_ptr_Function__ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData Function
|
||||||
|
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_desc_set]] %uint_32
|
||||||
; CHECK: OpSelectionMerge {{%\w+}} None
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: OpReturnValue %false
|
; CHECK: OpStore [[di_error]] %uint_1
|
||||||
|
; CHECK: OpBranch {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpAccessChain %_ptr_StorageBuffer__ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData %inst_bindless_input_buffer %uint_0 [[di_desc_set_idx]]
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
||||||
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpAccessChain %_ptr_StorageBuffer__ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData %inst_bindless_input_buffer %uint_0 [[di_desc_set]]
|
||||||
; CHECK: {{%\w+}} = OpLoad %_ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData {{%\w+}}
|
; CHECK: {{%\w+}} = OpLoad %_ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData {{%\w+}}
|
||||||
|
; CHECK: OpStore [[di_desc_set_ptr]] {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpBitcast %v2uint {{%\w+}}
|
; CHECK: {{%\w+}} = OpBitcast %v2uint {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpCompositeExtract %uint {{%\w+}} 0
|
; CHECK: {{%\w+}} = OpCompositeExtract %uint {{%\w+}} 0
|
||||||
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
||||||
@ -157,44 +170,96 @@ static const std::string kCheckDesc = R"(
|
|||||||
; CHECK: OpSelectionMerge {{%\w+}} None
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpFunctionCall %void %inst_bindless_stream_write_6 [[di_shader_id]] [[di_line]] [[di_stage_info]] %uint_1 [[di_desc_set_idx]] [[di_binding_idx]] [[di_desc_idx]] %uint_0 %uint_0
|
; CHECK: OpStore [[di_error]] %uint_1
|
||||||
; CHECK: OpReturnValue %false
|
; CHECK: OpBranch {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: OpBranch {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
||||||
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %_ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData [[di_desc_set_ptr]]
|
||||||
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_0
|
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_0
|
||||||
; CHECK: [[di_num_bindings:%\w+]] = OpLoad %uint {{%\w+}} Aligned 8
|
; CHECK: {{%\w+}} = OpLoad %uint {{%\w+}} Aligned 8
|
||||||
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_binding_idx]] [[di_num_bindings]]
|
; CHECK: OpStore [[di_num_bindings]] {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_binding]] {{%\w+}}
|
||||||
; CHECK: OpSelectionMerge {{%\w+}} None
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpFunctionCall %void %inst_bindless_stream_write_6 [[di_shader_id]] [[di_line]] [[di_stage_info]] %uint_1 [[di_desc_set_idx]] [[di_binding_idx]] [[di_desc_idx]] %uint_0 %uint_0
|
; CHECK: OpStore [[di_error]] %uint_1
|
||||||
; CHECK: OpReturnValue %false
|
; CHECK: OpBranch {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_1 [[di_binding_idx]]
|
; CHECK: OpBranch {{%\w+}}
|
||||||
; CHECK: [[di_desc_array_len:%\w+]] = OpLoad %uint {{%\w+}} Aligned 4
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_desc_idx]] [[di_desc_array_len]]
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
||||||
; CHECK: OpSelectionMerge {{%\w+}} None
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpFunctionCall %void %inst_bindless_stream_write_6 [[di_shader_id]] [[di_line]] [[di_stage_info]] %uint_1 [[di_desc_set_idx]] [[di_binding_idx]] [[di_desc_idx]] [[di_desc_array_len]] %uint_0
|
; CHECK: {{%\w+}} = OpLoad %_ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData [[di_desc_set_ptr]]
|
||||||
; CHECK: OpReturnValue %false
|
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_1 [[di_binding]]
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint {{%\w+}} Aligned 4
|
||||||
|
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_desc_idx]] {{%\w+}}
|
||||||
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpIAdd %uint {{%\w+}} {{%\w+}}
|
; CHECK: OpStore [[di_error]] %uint_1
|
||||||
|
; CHECK: OpStore [[di_param5]] {{%\w+}}
|
||||||
|
; CHECK: OpBranch {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: OpBranch {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpIEqual %bool %uint_0 {{%\w+}}
|
||||||
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %_ptr_PhysicalStorageBuffer_inst_bindless_DescriptorSetData [[di_desc_set_ptr]]
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_num_bindings]]
|
||||||
|
; CHECK: {{%\w+}} = OpIAdd %uint {{%\w+}} [[di_binding]]
|
||||||
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_1 {{%\w+}}
|
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_1 {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLoad %uint {{%\w+}} Aligned 4
|
; CHECK: {{%\w+}} = OpLoad %uint {{%\w+}} Aligned 4
|
||||||
|
; CHECK: {{%\w+}} = OpIAdd %uint {{%\w+}} [[di_desc_idx]]
|
||||||
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_1 {{%\w+}}
|
; CHECK: {{%\w+}} = OpAccessChain %_ptr_PhysicalStorageBuffer_uint {{%\w+}} %uint_1 {{%\w+}}
|
||||||
; CHECK: [[di_init_status:%\w+]] = OpLoad %uint {{%\w+}} Aligned 4
|
; CHECK: {{%\w+}} = OpLoad %uint {{%\w+}} Aligned 4
|
||||||
; CHECK: {{%\w+}} = OpIEqual %bool [[di_init_status]] %uint_0
|
; CHECK: OpStore [[di_init_status]] {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
||||||
; CHECK: OpSelectionMerge {{%\w+}} None
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpFunctionCall %void %inst_bindless_stream_write_6 [[di_shader_id]] [[di_line]] [[di_stage_info]] %uint_2 [[di_desc_set_idx]] [[di_binding_idx]] [[di_desc_idx]] %uint_0 %uint_0
|
; CHECK: OpStore [[di_error]] %uint_2
|
||||||
; CHECK: OpReturnValue %false
|
; CHECK: OpBranch {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool {{%\w+}} {{%\w+}}
|
; CHECK: OpBranch {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpIEqual %bool {{%\w+}} %uint_0
|
||||||
; CHECK: OpSelectionMerge {{%\w+}} None
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: {{%\w+}} = OpFunctionCall %void %inst_bindless_stream_write_6 [[di_shader_id]] [[di_line]] [[di_stage_info]] %uint_4 [[di_desc_set_idx]] [[di_binding_idx]] [[di_desc_idx]] [[di_byte_offset]] [[di_init_status]]
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_init_status]]
|
||||||
|
; CHECK: {{%\w+}} = OpUGreaterThanEqual %bool [[di_byte_offset]] {{%\w+}}
|
||||||
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: OpStore [[di_error]] %uint_4
|
||||||
|
; CHECK: OpStore [[di_param5]] [[di_byte_offset]]
|
||||||
|
; CHECK: OpStore [[di_param6]] {{%\w+}}
|
||||||
|
; CHECK: OpBranch {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: OpBranch {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_error]]
|
||||||
|
; CHECK: {{%\w+}} = OpINotEqual %bool %uint_0 {{%\w+}}
|
||||||
|
; CHECK: OpSelectionMerge {{%\w+}} None
|
||||||
|
; CHECK: OpBranchConditional {{%\w+}} {{%\w+}} {{%\w+}}
|
||||||
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_param5]]
|
||||||
|
; CHECK: {{%\w+}} = OpLoad %uint [[di_param6]]
|
||||||
|
; CHECK: {{%\w+}} = OpFunctionCall %void %inst_bindless_stream_write_6 [[di_shader_id]] [[di_line]] [[di_stage_info]] {{%\w+}} [[di_desc_set]] [[di_binding]] [[di_desc_idx]] {{%\w+}} {{%\w+}}
|
||||||
; CHECK: OpReturnValue %false
|
; CHECK: OpReturnValue %false
|
||||||
; CHECK: {{%\w+}} = OpLabel
|
; CHECK: {{%\w+}} = OpLabel
|
||||||
; CHECK: OpReturnValue %true
|
; CHECK: OpReturnValue %true
|
||||||
@ -4377,7 +4442,7 @@ TEST_F(InstBindlessTest, UniformMatrixRefRowMajor) {
|
|||||||
;CHECK: {{%\w+}} = OpLabel
|
;CHECK: {{%\w+}} = OpLabel
|
||||||
;CHECK: [[phi_result]] = OpPhi %float [[load_result]] {{%\w+}} [[null_float]] {{%\w+}}
|
;CHECK: [[phi_result]] = OpPhi %float [[load_result]] {{%\w+}} [[null_float]] {{%\w+}}
|
||||||
OpStore %v_vtxResult %21
|
OpStore %v_vtxResult %21
|
||||||
;CHECK-NOT: OpStore %v_vtxResult %21
|
;CHECK-NOT: OpStore %v_vtxResult %21$
|
||||||
;CHECK: OpStore %v_vtxResult [[phi_result]]
|
;CHECK: OpStore %v_vtxResult [[phi_result]]
|
||||||
OpReturn
|
OpReturn
|
||||||
OpFunctionEnd
|
OpFunctionEnd
|
||||||
@ -4493,7 +4558,7 @@ TEST_F(InstBindlessTest, UniformMatrixRefColumnMajor) {
|
|||||||
;CHECK: {{%\w+}} = OpLabel
|
;CHECK: {{%\w+}} = OpLabel
|
||||||
;CHECK: [[phi_result]] = OpPhi %float [[load_result]] {{%\w+}} [[null_float]] {{%\w+}}
|
;CHECK: [[phi_result]] = OpPhi %float [[load_result]] {{%\w+}} [[null_float]] {{%\w+}}
|
||||||
OpStore %v_vtxResult %21
|
OpStore %v_vtxResult %21
|
||||||
;CHECK-NOT: OpStore %v_vtxResult %21
|
;CHECK-NOT: OpStore %v_vtxResult %21$
|
||||||
;CHECK: OpStore %v_vtxResult [[phi_result]]
|
;CHECK: OpStore %v_vtxResult [[phi_result]]
|
||||||
OpReturn
|
OpReturn
|
||||||
OpFunctionEnd
|
OpFunctionEnd
|
||||||
|
Loading…
Reference in New Issue
Block a user