GrVkPipelineStateBuilder.cpp 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362
  1. /*
  2. * Copyright 2016 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. #include "include/gpu/GrContext.h"
  8. #include "src/gpu/GrContextPriv.h"
  9. #include "src/gpu/GrPersistentCacheUtils.h"
  10. #include "src/gpu/GrShaderCaps.h"
  11. #include "src/gpu/GrShaderUtils.h"
  12. #include "src/gpu/GrStencilSettings.h"
  13. #include "src/gpu/vk/GrVkDescriptorSetManager.h"
  14. #include "src/gpu/vk/GrVkGpu.h"
  15. #include "src/gpu/vk/GrVkPipelineStateBuilder.h"
  16. #include "src/gpu/vk/GrVkRenderPass.h"
  17. #include "src/gpu/vk/GrVkRenderTarget.h"
  18. typedef size_t shader_size;
  19. GrVkPipelineState* GrVkPipelineStateBuilder::CreatePipelineState(
  20. GrVkGpu* gpu,
  21. GrRenderTarget* renderTarget, GrSurfaceOrigin origin,
  22. const GrPrimitiveProcessor& primProc,
  23. const GrTextureProxy* const primProcProxies[],
  24. const GrPipeline& pipeline,
  25. const GrStencilSettings& stencil,
  26. GrPrimitiveType primitiveType,
  27. Desc* desc,
  28. VkRenderPass compatibleRenderPass) {
  29. // create a builder. This will be handed off to effects so they can use it to add
  30. // uniforms, varyings, textures, etc
  31. GrVkPipelineStateBuilder builder(gpu, renderTarget, origin, pipeline, primProc,
  32. primProcProxies, desc);
  33. if (!builder.emitAndInstallProcs()) {
  34. return nullptr;
  35. }
  36. return builder.finalize(stencil, primitiveType, compatibleRenderPass, desc);
  37. }
  38. GrVkPipelineStateBuilder::GrVkPipelineStateBuilder(GrVkGpu* gpu,
  39. GrRenderTarget* renderTarget,
  40. GrSurfaceOrigin origin,
  41. const GrPipeline& pipeline,
  42. const GrPrimitiveProcessor& primProc,
  43. const GrTextureProxy* const primProcProxies[],
  44. GrProgramDesc* desc)
  45. : INHERITED(renderTarget, origin, primProc, primProcProxies, pipeline, desc)
  46. , fGpu(gpu)
  47. , fVaryingHandler(this)
  48. , fUniformHandler(this) {}
  49. const GrCaps* GrVkPipelineStateBuilder::caps() const {
  50. return fGpu->caps();
  51. }
  52. void GrVkPipelineStateBuilder::finalizeFragmentOutputColor(GrShaderVar& outputColor) {
  53. outputColor.addLayoutQualifier("location = 0, index = 0");
  54. }
  55. void GrVkPipelineStateBuilder::finalizeFragmentSecondaryColor(GrShaderVar& outputColor) {
  56. outputColor.addLayoutQualifier("location = 0, index = 1");
  57. }
  58. bool GrVkPipelineStateBuilder::createVkShaderModule(VkShaderStageFlagBits stage,
  59. const SkSL::String& sksl,
  60. VkShaderModule* shaderModule,
  61. VkPipelineShaderStageCreateInfo* stageInfo,
  62. const SkSL::Program::Settings& settings,
  63. Desc* desc,
  64. SkSL::String* outSPIRV,
  65. SkSL::Program::Inputs* outInputs) {
  66. if (!GrCompileVkShaderModule(fGpu, sksl, stage, shaderModule,
  67. stageInfo, settings, outSPIRV, outInputs)) {
  68. return false;
  69. }
  70. if (outInputs->fRTHeight) {
  71. this->addRTHeightUniform(SKSL_RTHEIGHT_NAME);
  72. }
  73. return true;
  74. }
  75. bool GrVkPipelineStateBuilder::installVkShaderModule(VkShaderStageFlagBits stage,
  76. const GrGLSLShaderBuilder& builder,
  77. VkShaderModule* shaderModule,
  78. VkPipelineShaderStageCreateInfo* stageInfo,
  79. SkSL::String spirv,
  80. SkSL::Program::Inputs inputs) {
  81. if (!GrInstallVkShaderModule(fGpu, spirv, stage, shaderModule, stageInfo)) {
  82. return false;
  83. }
  84. if (inputs.fRTHeight) {
  85. this->addRTHeightUniform(SKSL_RTHEIGHT_NAME);
  86. }
  87. return true;
  88. }
  89. static constexpr SkFourByteTag kSPIRV_Tag = SkSetFourByteTag('S', 'P', 'R', 'V');
  90. static constexpr SkFourByteTag kSKSL_Tag = SkSetFourByteTag('S', 'K', 'S', 'L');
  91. int GrVkPipelineStateBuilder::loadShadersFromCache(const SkData& cached,
  92. VkShaderModule outShaderModules[],
  93. VkPipelineShaderStageCreateInfo* outStageInfo) {
  94. SkSL::String shaders[kGrShaderTypeCount];
  95. SkSL::Program::Inputs inputs[kGrShaderTypeCount];
  96. if (kSPIRV_Tag != GrPersistentCacheUtils::UnpackCachedShaders(&cached, shaders,
  97. inputs, kGrShaderTypeCount)) {
  98. return 0;
  99. }
  100. SkAssertResult(this->installVkShaderModule(VK_SHADER_STAGE_VERTEX_BIT,
  101. fVS,
  102. &outShaderModules[kVertex_GrShaderType],
  103. &outStageInfo[0],
  104. shaders[kVertex_GrShaderType],
  105. inputs[kVertex_GrShaderType]));
  106. SkAssertResult(this->installVkShaderModule(VK_SHADER_STAGE_FRAGMENT_BIT,
  107. fFS,
  108. &outShaderModules[kFragment_GrShaderType],
  109. &outStageInfo[1],
  110. shaders[kFragment_GrShaderType],
  111. inputs[kFragment_GrShaderType]));
  112. if (!shaders[kGeometry_GrShaderType].empty()) {
  113. SkAssertResult(this->installVkShaderModule(VK_SHADER_STAGE_GEOMETRY_BIT,
  114. fGS,
  115. &outShaderModules[kGeometry_GrShaderType],
  116. &outStageInfo[2],
  117. shaders[kGeometry_GrShaderType],
  118. inputs[kGeometry_GrShaderType]));
  119. return 3;
  120. } else {
  121. return 2;
  122. }
  123. }
  124. void GrVkPipelineStateBuilder::storeShadersInCache(const SkSL::String shaders[],
  125. const SkSL::Program::Inputs inputs[],
  126. bool isSkSL) {
  127. Desc* desc = static_cast<Desc*>(this->desc());
  128. sk_sp<SkData> key = SkData::MakeWithoutCopy(desc->asKey(), desc->shaderKeyLength());
  129. sk_sp<SkData> data = GrPersistentCacheUtils::PackCachedShaders(isSkSL ? kSKSL_Tag : kSPIRV_Tag,
  130. shaders,
  131. inputs, kGrShaderTypeCount);
  132. this->gpu()->getContext()->priv().getPersistentCache()->store(*key, *data);
  133. }
  134. GrVkPipelineState* GrVkPipelineStateBuilder::finalize(const GrStencilSettings& stencil,
  135. GrPrimitiveType primitiveType,
  136. VkRenderPass compatibleRenderPass,
  137. Desc* desc) {
  138. VkDescriptorSetLayout dsLayout[2];
  139. VkPipelineLayout pipelineLayout;
  140. VkShaderModule shaderModules[kGrShaderTypeCount] = { VK_NULL_HANDLE,
  141. VK_NULL_HANDLE,
  142. VK_NULL_HANDLE };
  143. GrVkResourceProvider& resourceProvider = fGpu->resourceProvider();
  144. // These layouts are not owned by the PipelineStateBuilder and thus should not be destroyed
  145. dsLayout[GrVkUniformHandler::kUniformBufferDescSet] = resourceProvider.getUniformDSLayout();
  146. GrVkDescriptorSetManager::Handle samplerDSHandle;
  147. resourceProvider.getSamplerDescriptorSetHandle(VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER,
  148. fUniformHandler, &samplerDSHandle);
  149. dsLayout[GrVkUniformHandler::kSamplerDescSet] =
  150. resourceProvider.getSamplerDSLayout(samplerDSHandle);
  151. // Create the VkPipelineLayout
  152. VkPipelineLayoutCreateInfo layoutCreateInfo;
  153. memset(&layoutCreateInfo, 0, sizeof(VkPipelineLayoutCreateFlags));
  154. layoutCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO;
  155. layoutCreateInfo.pNext = 0;
  156. layoutCreateInfo.flags = 0;
  157. layoutCreateInfo.setLayoutCount = 2;
  158. layoutCreateInfo.pSetLayouts = dsLayout;
  159. layoutCreateInfo.pushConstantRangeCount = 0;
  160. layoutCreateInfo.pPushConstantRanges = nullptr;
  161. GR_VK_CALL_ERRCHECK(fGpu->vkInterface(), CreatePipelineLayout(fGpu->device(),
  162. &layoutCreateInfo,
  163. nullptr,
  164. &pipelineLayout));
  165. // We need to enable the following extensions so that the compiler can correctly make spir-v
  166. // from our glsl shaders.
  167. fVS.extensions().appendf("#extension GL_ARB_separate_shader_objects : enable\n");
  168. fFS.extensions().appendf("#extension GL_ARB_separate_shader_objects : enable\n");
  169. fVS.extensions().appendf("#extension GL_ARB_shading_language_420pack : enable\n");
  170. fFS.extensions().appendf("#extension GL_ARB_shading_language_420pack : enable\n");
  171. this->finalizeShaders();
  172. VkPipelineShaderStageCreateInfo shaderStageInfo[3];
  173. SkSL::Program::Settings settings;
  174. settings.fCaps = this->caps()->shaderCaps();
  175. settings.fFlipY = this->origin() != kTopLeft_GrSurfaceOrigin;
  176. settings.fSharpenTextures =
  177. this->gpu()->getContext()->priv().options().fSharpenMipmappedTextures;
  178. SkASSERT(!this->fragColorIsInOut());
  179. sk_sp<SkData> cached;
  180. auto persistentCache = fGpu->getContext()->priv().getPersistentCache();
  181. if (persistentCache) {
  182. sk_sp<SkData> key = SkData::MakeWithoutCopy(desc->asKey(), desc->shaderKeyLength());
  183. cached = persistentCache->load(*key);
  184. }
  185. bool binaryCache = true;
  186. #if GR_TEST_UTILS
  187. binaryCache = !fGpu->getContext()->priv().options().fCacheSKSL;
  188. #endif
  189. int numShaderStages = 0;
  190. if (cached && binaryCache) {
  191. numShaderStages = this->loadShadersFromCache(*cached, shaderModules, shaderStageInfo);
  192. }
  193. if (!numShaderStages) {
  194. numShaderStages = 2; // We always have at least vertex and fragment stages.
  195. SkSL::String shaders[kGrShaderTypeCount];
  196. SkSL::Program::Inputs inputs[kGrShaderTypeCount];
  197. SkSL::String* sksl[kGrShaderTypeCount] = {
  198. &fVS.fCompilerString,
  199. &fGS.fCompilerString,
  200. &fFS.fCompilerString,
  201. };
  202. #if GR_TEST_UTILS
  203. SkSL::String cached_sksl[kGrShaderTypeCount];
  204. if (cached) {
  205. if (kSKSL_Tag == GrPersistentCacheUtils::UnpackCachedShaders(
  206. cached.get(), cached_sksl, inputs, kGrShaderTypeCount)) {
  207. for (int i = 0; i < kGrShaderTypeCount; ++i) {
  208. sksl[i] = &cached_sksl[i];
  209. }
  210. }
  211. }
  212. #endif
  213. bool success = this->createVkShaderModule(VK_SHADER_STAGE_VERTEX_BIT,
  214. *sksl[kVertex_GrShaderType],
  215. &shaderModules[kVertex_GrShaderType],
  216. &shaderStageInfo[0],
  217. settings,
  218. desc,
  219. &shaders[kVertex_GrShaderType],
  220. &inputs[kVertex_GrShaderType]);
  221. success = success && this->createVkShaderModule(VK_SHADER_STAGE_FRAGMENT_BIT,
  222. *sksl[kFragment_GrShaderType],
  223. &shaderModules[kFragment_GrShaderType],
  224. &shaderStageInfo[1],
  225. settings,
  226. desc,
  227. &shaders[kFragment_GrShaderType],
  228. &inputs[kFragment_GrShaderType]);
  229. if (this->primitiveProcessor().willUseGeoShader()) {
  230. success = success && this->createVkShaderModule(VK_SHADER_STAGE_GEOMETRY_BIT,
  231. *sksl[kGeometry_GrShaderType],
  232. &shaderModules[kGeometry_GrShaderType],
  233. &shaderStageInfo[2],
  234. settings,
  235. desc,
  236. &shaders[kGeometry_GrShaderType],
  237. &inputs[kGeometry_GrShaderType]);
  238. ++numShaderStages;
  239. }
  240. if (!success) {
  241. for (int i = 0; i < kGrShaderTypeCount; ++i) {
  242. if (shaderModules[i]) {
  243. GR_VK_CALL(fGpu->vkInterface(), DestroyShaderModule(fGpu->device(),
  244. shaderModules[i], nullptr));
  245. }
  246. }
  247. GR_VK_CALL(fGpu->vkInterface(), DestroyPipelineLayout(fGpu->device(), pipelineLayout,
  248. nullptr));
  249. return nullptr;
  250. }
  251. if (persistentCache && !cached) {
  252. bool isSkSL = false;
  253. #if GR_TEST_UTILS
  254. if (fGpu->getContext()->priv().options().fCacheSKSL) {
  255. for (int i = 0; i < kGrShaderTypeCount; ++i) {
  256. shaders[i] = GrShaderUtils::PrettyPrint(*sksl[i]);
  257. }
  258. isSkSL = true;
  259. }
  260. #endif
  261. this->storeShadersInCache(shaders, inputs, isSkSL);
  262. }
  263. }
  264. GrVkPipeline* pipeline = resourceProvider.createPipeline(
  265. this->renderTarget()->numSamples(), fPrimProc, fPipeline, stencil, this->origin(),
  266. shaderStageInfo, numShaderStages, primitiveType, compatibleRenderPass, pipelineLayout);
  267. for (int i = 0; i < kGrShaderTypeCount; ++i) {
  268. // This if check should not be needed since calling destroy on a VK_NULL_HANDLE is allowed.
  269. // However this is causing a crash in certain drivers (e.g. NVidia).
  270. if (shaderModules[i]) {
  271. GR_VK_CALL(fGpu->vkInterface(), DestroyShaderModule(fGpu->device(), shaderModules[i],
  272. nullptr));
  273. }
  274. }
  275. if (!pipeline) {
  276. GR_VK_CALL(fGpu->vkInterface(), DestroyPipelineLayout(fGpu->device(), pipelineLayout,
  277. nullptr));
  278. return nullptr;
  279. }
  280. return new GrVkPipelineState(fGpu,
  281. pipeline,
  282. pipelineLayout,
  283. samplerDSHandle,
  284. fUniformHandles,
  285. fUniformHandler.fUniforms,
  286. fUniformHandler.fCurrentGeometryUBOOffset,
  287. fUniformHandler.fCurrentFragmentUBOOffset,
  288. fUniformHandler.fSamplers,
  289. std::move(fGeometryProcessor),
  290. std::move(fXferProcessor),
  291. std::move(fFragmentProcessors),
  292. fFragmentProcessorCnt);
  293. }
  294. //////////////////////////////////////////////////////////////////////////////
  295. bool GrVkPipelineStateBuilder::Desc::Build(Desc* desc,
  296. GrRenderTarget* renderTarget,
  297. const GrPrimitiveProcessor& primProc,
  298. const GrPipeline& pipeline,
  299. const GrStencilSettings& stencil,
  300. GrPrimitiveType primitiveType,
  301. GrVkGpu* gpu) {
  302. if (!INHERITED::Build(desc, renderTarget, primProc,
  303. primitiveType == GrPrimitiveType::kPoints, pipeline, gpu)) {
  304. return false;
  305. }
  306. GrProcessorKeyBuilder b(&desc->key());
  307. b.add32(GrVkGpu::kShader_PersistentCacheKeyType);
  308. int keyLength = desc->key().count();
  309. SkASSERT(0 == (keyLength % 4));
  310. desc->fShaderKeyLength = SkToU32(keyLength);
  311. GrVkRenderTarget* vkRT = (GrVkRenderTarget*)renderTarget;
  312. vkRT->simpleRenderPass()->genKey(&b);
  313. stencil.genKey(&b);
  314. b.add32(pipeline.getBlendInfoKey());
  315. b.add32((uint32_t)primitiveType);
  316. return true;
  317. }