| 127 | } |
| 128 | |
| 129 | spv_result_t ValidateSelect(ValidationState_t& _, const Instruction* inst, |
| 130 | uint32_t operand_index = 2) { |
| 131 | const spv::Op opcode = inst->opcode(); |
| 132 | const uint32_t result_type = inst->type_id(); |
| 133 | uint32_t dimension = 1; |
| 134 | const Instruction* type_inst = _.FindDef(result_type); |
| 135 | assert(type_inst); |
| 136 | |
| 137 | const auto composites = _.features().select_between_composites; |
| 138 | auto fail = [&_, composites, inst, opcode]() -> spv_result_t { |
| 139 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 140 | << "Expected scalar or " << (composites ? "composite" : "vector") |
| 141 | << " type as Result Type: " << spvOpcodeString(opcode); |
| 142 | }; |
| 143 | |
| 144 | const spv::Op type_opcode = type_inst->opcode(); |
| 145 | switch (type_opcode) { |
| 146 | case spv::Op::OpTypeUntypedPointerKHR: |
| 147 | case spv::Op::OpTypePointer: { |
| 148 | if (_.addressing_model() == spv::AddressingModel::Logical && |
| 149 | !_.HasCapability(spv::Capability::VariablePointersStorageBuffer)) |
| 150 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 151 | << "Using pointers with OpSelect requires capability " |
| 152 | << "VariablePointers or VariablePointersStorageBuffer"; |
| 153 | break; |
| 154 | } |
| 155 | |
| 156 | case spv::Op::OpTypeSampledImage: |
| 157 | case spv::Op::OpTypeImage: |
| 158 | case spv::Op::OpTypeSampler: { |
| 159 | if (!_.HasCapability(spv::Capability::BindlessTextureNV)) |
| 160 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 161 | << "Using image/sampler with OpSelect requires capability " |
| 162 | << "BindlessTextureNV"; |
| 163 | break; |
| 164 | } |
| 165 | |
| 166 | case spv::Op::OpTypeVector: { |
| 167 | dimension = type_inst->word(3); |
| 168 | break; |
| 169 | } |
| 170 | case spv::Op::OpTypeVectorIdEXT: { |
| 171 | dimension = _.GetDimension(result_type); |
| 172 | break; |
| 173 | } |
| 174 | |
| 175 | case spv::Op::OpTypeBool: |
| 176 | case spv::Op::OpTypeInt: |
| 177 | case spv::Op::OpTypeFloat: { |
| 178 | break; |
| 179 | } |
| 180 | |
| 181 | // Not RuntimeArray because of other rules. |
| 182 | case spv::Op::OpTypeArray: |
| 183 | case spv::Op::OpTypeMatrix: |
| 184 | case spv::Op::OpTypeStruct: { |
| 185 | if (!composites) return fail(); |
| 186 | break; |
no test coverage detected