1 /*
2 * Copyright 2015 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8 #include "src/gpu/vk/GrVkUtil.h"
9
10 #include "src/gpu/GrContextPriv.h"
11 #include "src/gpu/GrDataUtils.h"
12 #include "src/gpu/vk/GrVkGpu.h"
13 #include "src/sksl/SkSLCompiler.h"
14
15 #ifdef SK_DEBUG
GrVkFormatColorTypePairIsValid(VkFormat format,GrColorType colorType)16 bool GrVkFormatColorTypePairIsValid(VkFormat format, GrColorType colorType) {
17 switch (format) {
18 case VK_FORMAT_R8G8B8A8_UNORM: return GrColorType::kRGBA_8888 == colorType ||
19 GrColorType::kRGB_888x == colorType;
20 case VK_FORMAT_B8G8R8A8_UNORM: return GrColorType::kBGRA_8888 == colorType;
21 case VK_FORMAT_R8G8B8A8_SRGB: return GrColorType::kRGBA_8888_SRGB == colorType;
22 case VK_FORMAT_R8G8B8_UNORM: return GrColorType::kRGB_888x == colorType;
23 case VK_FORMAT_R8G8_UNORM: return GrColorType::kRG_88 == colorType;
24 case VK_FORMAT_A2B10G10R10_UNORM_PACK32: return GrColorType::kRGBA_1010102 == colorType;
25 case VK_FORMAT_A2R10G10B10_UNORM_PACK32: return GrColorType::kBGRA_1010102 == colorType;
26 case VK_FORMAT_R5G6B5_UNORM_PACK16: return GrColorType::kBGR_565 == colorType;
27 // R4G4B4A4 is not required to be supported so we actually
28 // store RGBA_4444 data as B4G4R4A4.
29 case VK_FORMAT_B4G4R4A4_UNORM_PACK16: return GrColorType::kABGR_4444 == colorType;
30 case VK_FORMAT_R4G4B4A4_UNORM_PACK16: return GrColorType::kABGR_4444 == colorType;
31 case VK_FORMAT_R8_UNORM: return GrColorType::kAlpha_8 == colorType ||
32 GrColorType::kGray_8 == colorType;
33 case VK_FORMAT_R16G16B16A16_SFLOAT: return GrColorType::kRGBA_F16 == colorType ||
34 GrColorType::kRGBA_F16_Clamped == colorType;
35 case VK_FORMAT_R16_SFLOAT: return GrColorType::kAlpha_F16 == colorType;
36 case VK_FORMAT_R16_UNORM: return GrColorType::kAlpha_16 == colorType;
37 case VK_FORMAT_R16G16_UNORM: return GrColorType::kRG_1616 == colorType;
38 case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM: return GrColorType::kRGB_888x == colorType;
39 case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM: return GrColorType::kRGB_888x == colorType;
40 case VK_FORMAT_R16G16B16A16_UNORM: return GrColorType::kRGBA_16161616 == colorType;
41 case VK_FORMAT_R16G16_SFLOAT: return GrColorType::kRG_F16 == colorType;
42 case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK: return GrColorType::kRGB_888x == colorType;
43 case VK_FORMAT_BC1_RGB_UNORM_BLOCK: return GrColorType::kRGB_888x == colorType;
44 case VK_FORMAT_BC1_RGBA_UNORM_BLOCK: return GrColorType::kRGBA_8888 == colorType;
45 default: return false;
46 }
47
48 SkUNREACHABLE;
49 }
50 #endif
51
GrVkFormatIsSupported(VkFormat format)52 bool GrVkFormatIsSupported(VkFormat format) {
53 switch (format) {
54 case VK_FORMAT_R8G8B8A8_UNORM:
55 case VK_FORMAT_B8G8R8A8_UNORM:
56 case VK_FORMAT_R8G8B8A8_SRGB:
57 case VK_FORMAT_R8G8B8_UNORM:
58 case VK_FORMAT_R8G8_UNORM:
59 case VK_FORMAT_A2B10G10R10_UNORM_PACK32:
60 case VK_FORMAT_A2R10G10B10_UNORM_PACK32:
61 case VK_FORMAT_R5G6B5_UNORM_PACK16:
62 case VK_FORMAT_B4G4R4A4_UNORM_PACK16:
63 case VK_FORMAT_R4G4B4A4_UNORM_PACK16:
64 case VK_FORMAT_R8_UNORM:
65 case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK:
66 case VK_FORMAT_BC1_RGB_UNORM_BLOCK:
67 case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:
68 case VK_FORMAT_R16G16B16A16_SFLOAT:
69 case VK_FORMAT_R16_SFLOAT:
70 case VK_FORMAT_R16_UNORM:
71 case VK_FORMAT_R16G16_UNORM:
72 case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM:
73 case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM:
74 case VK_FORMAT_R16G16B16A16_UNORM:
75 case VK_FORMAT_R16G16_SFLOAT:
76 return true;
77 default:
78 return false;
79 }
80 }
81
GrVkFormatNeedsYcbcrSampler(VkFormat format)82 bool GrVkFormatNeedsYcbcrSampler(VkFormat format) {
83 return format == VK_FORMAT_G8_B8R8_2PLANE_420_UNORM ||
84 format == VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM;
85 }
86
GrSampleCountToVkSampleCount(uint32_t samples,VkSampleCountFlagBits * vkSamples)87 bool GrSampleCountToVkSampleCount(uint32_t samples, VkSampleCountFlagBits* vkSamples) {
88 SkASSERT(samples >= 1);
89 switch (samples) {
90 case 1:
91 *vkSamples = VK_SAMPLE_COUNT_1_BIT;
92 return true;
93 case 2:
94 *vkSamples = VK_SAMPLE_COUNT_2_BIT;
95 return true;
96 case 4:
97 *vkSamples = VK_SAMPLE_COUNT_4_BIT;
98 return true;
99 case 8:
100 *vkSamples = VK_SAMPLE_COUNT_8_BIT;
101 return true;
102 case 16:
103 *vkSamples = VK_SAMPLE_COUNT_16_BIT;
104 return true;
105 default:
106 return false;
107 }
108 }
109
vk_shader_stage_to_skiasl_kind(VkShaderStageFlagBits stage)110 SkSL::Program::Kind vk_shader_stage_to_skiasl_kind(VkShaderStageFlagBits stage) {
111 if (VK_SHADER_STAGE_VERTEX_BIT == stage) {
112 return SkSL::Program::kVertex_Kind;
113 }
114 if (VK_SHADER_STAGE_GEOMETRY_BIT == stage) {
115 return SkSL::Program::kGeometry_Kind;
116 }
117 SkASSERT(VK_SHADER_STAGE_FRAGMENT_BIT == stage);
118 return SkSL::Program::kFragment_Kind;
119 }
120
GrCompileVkShaderModule(GrVkGpu * gpu,const SkSL::String & shaderString,VkShaderStageFlagBits stage,VkShaderModule * shaderModule,VkPipelineShaderStageCreateInfo * stageInfo,const SkSL::Program::Settings & settings,SkSL::String * outSPIRV,SkSL::Program::Inputs * outInputs)121 bool GrCompileVkShaderModule(GrVkGpu* gpu,
122 const SkSL::String& shaderString,
123 VkShaderStageFlagBits stage,
124 VkShaderModule* shaderModule,
125 VkPipelineShaderStageCreateInfo* stageInfo,
126 const SkSL::Program::Settings& settings,
127 SkSL::String* outSPIRV,
128 SkSL::Program::Inputs* outInputs) {
129 auto errorHandler = gpu->getContext()->priv().getShaderErrorHandler();
130 std::unique_ptr<SkSL::Program> program = gpu->shaderCompiler()->convertProgram(
131 vk_shader_stage_to_skiasl_kind(stage), shaderString, settings);
132 if (!program) {
133 errorHandler->compileError(shaderString.c_str(),
134 gpu->shaderCompiler()->errorText().c_str());
135 return false;
136 }
137 *outInputs = program->fInputs;
138 if (!gpu->shaderCompiler()->toSPIRV(*program, outSPIRV)) {
139 errorHandler->compileError(shaderString.c_str(),
140 gpu->shaderCompiler()->errorText().c_str());
141 return false;
142 }
143
144 return GrInstallVkShaderModule(gpu, *outSPIRV, stage, shaderModule, stageInfo);
145 }
146
GrInstallVkShaderModule(GrVkGpu * gpu,const SkSL::String & spirv,VkShaderStageFlagBits stage,VkShaderModule * shaderModule,VkPipelineShaderStageCreateInfo * stageInfo)147 bool GrInstallVkShaderModule(GrVkGpu* gpu,
148 const SkSL::String& spirv,
149 VkShaderStageFlagBits stage,
150 VkShaderModule* shaderModule,
151 VkPipelineShaderStageCreateInfo* stageInfo) {
152 VkShaderModuleCreateInfo moduleCreateInfo;
153 memset(&moduleCreateInfo, 0, sizeof(VkShaderModuleCreateInfo));
154 moduleCreateInfo.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
155 moduleCreateInfo.pNext = nullptr;
156 moduleCreateInfo.flags = 0;
157 moduleCreateInfo.codeSize = spirv.size();
158 moduleCreateInfo.pCode = (const uint32_t*)spirv.c_str();
159
160 VkResult err;
161 GR_VK_CALL_RESULT(gpu, err, CreateShaderModule(gpu->device(), &moduleCreateInfo, nullptr,
162 shaderModule));
163 if (err) {
164 return false;
165 }
166
167 memset(stageInfo, 0, sizeof(VkPipelineShaderStageCreateInfo));
168 stageInfo->sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO;
169 stageInfo->pNext = nullptr;
170 stageInfo->flags = 0;
171 stageInfo->stage = stage;
172 stageInfo->module = *shaderModule;
173 stageInfo->pName = "main";
174 stageInfo->pSpecializationInfo = nullptr;
175
176 return true;
177 }
178
GrVkFormatIsCompressed(VkFormat vkFormat)179 bool GrVkFormatIsCompressed(VkFormat vkFormat) {
180 switch (vkFormat) {
181 case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK:
182 case VK_FORMAT_BC1_RGB_UNORM_BLOCK:
183 case VK_FORMAT_BC1_RGBA_UNORM_BLOCK:
184 return true;
185 default:
186 return false;
187 }
188 SkUNREACHABLE;
189 }
190
GrVkFormatToCompressionType(VkFormat vkFormat)191 SkImage::CompressionType GrVkFormatToCompressionType(VkFormat vkFormat) {
192 switch (vkFormat) {
193 case VK_FORMAT_ETC2_R8G8B8_UNORM_BLOCK: return SkImage::CompressionType::kETC2_RGB8_UNORM;
194 case VK_FORMAT_BC1_RGB_UNORM_BLOCK: return SkImage::CompressionType::kBC1_RGB8_UNORM;
195 case VK_FORMAT_BC1_RGBA_UNORM_BLOCK: return SkImage::CompressionType::kBC1_RGBA8_UNORM;
196 default: return SkImage::CompressionType::kNone;
197 }
198 SkUNREACHABLE;
199 }
200