| 634 | } |
| 635 | |
| 636 | spv_result_t ValidateStorageClass(ValidationState_t& _, |
| 637 | const Instruction* entry_point) { |
| 638 | bool has_push_constant = false; |
| 639 | bool has_ray_payload = false; |
| 640 | bool has_hit_attribute = false; |
| 641 | bool has_callable_data = false; |
| 642 | for (uint32_t i = 3; i < entry_point->operands().size(); ++i) { |
| 643 | auto interface_id = entry_point->GetOperandAs<uint32_t>(i); |
| 644 | auto interface_var = _.FindDef(interface_id); |
| 645 | auto storage_class = interface_var->GetOperandAs<spv::StorageClass>(2); |
| 646 | switch (storage_class) { |
| 647 | case spv::StorageClass::PushConstant: { |
| 648 | if (has_push_constant && |
| 649 | !(_.HasCapability(spv::Capability::PushConstantBanksNV))) { |
| 650 | return _.diag(SPV_ERROR_INVALID_DATA, entry_point) |
| 651 | << _.VkErrorID(6673) |
| 652 | << "Entry-point has more than one variable with the " |
| 653 | "PushConstant storage class in the interface"; |
| 654 | } |
| 655 | has_push_constant = true; |
| 656 | break; |
| 657 | } |
| 658 | case spv::StorageClass::IncomingRayPayloadKHR: { |
| 659 | if (has_ray_payload) { |
| 660 | return _.diag(SPV_ERROR_INVALID_DATA, entry_point) |
| 661 | << _.VkErrorID(4700) |
| 662 | << "Entry-point has more than one variable with the " |
| 663 | "IncomingRayPayloadKHR storage class in the interface"; |
| 664 | } |
| 665 | has_ray_payload = true; |
| 666 | break; |
| 667 | } |
| 668 | case spv::StorageClass::HitAttributeKHR: { |
| 669 | if (has_hit_attribute) { |
| 670 | return _.diag(SPV_ERROR_INVALID_DATA, entry_point) |
| 671 | << _.VkErrorID(4702) |
| 672 | << "Entry-point has more than one variable with the " |
| 673 | "HitAttributeKHR storage class in the interface"; |
| 674 | } |
| 675 | has_hit_attribute = true; |
| 676 | break; |
| 677 | } |
| 678 | case spv::StorageClass::IncomingCallableDataKHR: { |
| 679 | if (has_callable_data) { |
| 680 | return _.diag(SPV_ERROR_INVALID_DATA, entry_point) |
| 681 | << _.VkErrorID(4706) |
| 682 | << "Entry-point has more than one variable with the " |
| 683 | "IncomingCallableDataKHR storage class in the interface"; |
| 684 | } |
| 685 | has_callable_data = true; |
| 686 | break; |
| 687 | } |
| 688 | case spv::StorageClass::Input: |
| 689 | case spv::StorageClass::Output: { |
| 690 | auto result_type = _.FindDef(interface_var->type_id()); |
| 691 | if (_.ContainsType(result_type->GetOperandAs<uint32_t>(2), |
| 692 | [](const Instruction* inst) { |
| 693 | if (inst && |
no test coverage detected