| 1883 | } |
| 1884 | |
| 1885 | spv_result_t ValidateImageRead(ValidationState_t& _, const Instruction* inst) { |
| 1886 | const spv::Op opcode = inst->opcode(); |
| 1887 | uint32_t actual_result_type = 0; |
| 1888 | if (spv_result_t error = GetActualResultType(_, inst, &actual_result_type)) { |
| 1889 | return error; |
| 1890 | } |
| 1891 | |
| 1892 | if (!_.IsIntScalarOrVectorType(actual_result_type) && |
| 1893 | !_.IsFloatScalarOrVectorType(actual_result_type)) { |
| 1894 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 1895 | << "Expected " << GetActualResultTypeStr(opcode) |
| 1896 | << " to be int or float scalar or vector type"; |
| 1897 | } |
| 1898 | |
| 1899 | const auto target_env = _.context()->target_env; |
| 1900 | // Vulkan requires the result to be a 4-element int or float |
| 1901 | // vector. |
| 1902 | if (spvIsVulkanEnv(target_env)) { |
| 1903 | if (_.GetDimension(actual_result_type) != 4) { |
| 1904 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 1905 | << _.VkErrorID(4780) << "Expected " |
| 1906 | << GetActualResultTypeStr(opcode) << " to have 4 components"; |
| 1907 | } |
| 1908 | } // Check OpenCL below, after we get the image info. |
| 1909 | |
| 1910 | const uint32_t image_type = _.GetOperandTypeId(inst, 2); |
| 1911 | if (_.GetIdOpcode(image_type) != spv::Op::OpTypeImage) { |
| 1912 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 1913 | << "Expected Image to be of type OpTypeImage"; |
| 1914 | } |
| 1915 | |
| 1916 | ImageTypeInfo info; |
| 1917 | if (!GetImageTypeInfo(_, image_type, &info)) { |
| 1918 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 1919 | << "Corrupt image type definition"; |
| 1920 | } |
| 1921 | |
| 1922 | if (spvIsOpenCLEnv(target_env)) { |
| 1923 | // In OpenCL, a read from a depth image returns a scalar float. In other |
| 1924 | // cases, the result is always a 4-element vector. |
| 1925 | // https://www.khronos.org/registry/OpenCL/specs/3.0-unified/html/OpenCL_Env.html#_data_format_for_reading_and_writing_images |
| 1926 | // https://www.khronos.org/registry/OpenCL/specs/3.0-unified/html/OpenCL_C.html#image-read-and-write-functions |
| 1927 | // The builtins for reading depth images are: |
| 1928 | // float read_imagef(aQual image2d_depth_t image, int2 coord) |
| 1929 | // float read_imagef(aQual image2d_array_depth_t image, int4 coord) |
| 1930 | if (info.depth) { |
| 1931 | if (!_.IsFloatScalarType(actual_result_type)) { |
| 1932 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 1933 | << "Expected " << GetActualResultTypeStr(opcode) |
| 1934 | << " from a depth image read to result in a scalar float value"; |
| 1935 | } |
| 1936 | } else { |
| 1937 | if (_.GetDimension(actual_result_type) != 4) { |
| 1938 | return _.diag(SPV_ERROR_INVALID_DATA, inst) |
| 1939 | << "Expected " << GetActualResultTypeStr(opcode) |
| 1940 | << " to have 4 components"; |
| 1941 | } |
| 1942 | } |
no test coverage detected