GrSkSLFP.h 6.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182
  1. /*
  2. * Copyright 2018 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. #ifndef GrSkSLFP_DEFINED
  8. #define GrSkSLFP_DEFINED
  9. #include "include/core/SkRefCnt.h"
  10. #include "src/gpu/GrCaps.h"
  11. #include "src/gpu/GrCoordTransform.h"
  12. #include "src/gpu/GrFragmentProcessor.h"
  13. #include "src/gpu/GrShaderCaps.h"
  14. #include "src/gpu/GrSkSLFPFactoryCache.h"
  15. #include "src/sksl/SkSLCompiler.h"
  16. #include "src/sksl/SkSLPipelineStageCodeGenerator.h"
  17. #include <atomic>
  18. #if GR_TEST_UTILS
  19. #define GR_FP_SRC_STRING const char*
  20. #else
  21. #define GR_FP_SRC_STRING static const char*
  22. #endif
  23. class GrContext_Base;
  24. class GrSkSLFPFactory;
  25. class GrSkSLFP : public GrFragmentProcessor {
  26. public:
  27. /**
  28. * Returns a new unique identifier. Each different SkSL fragment processor should call
  29. * NewIndex once, statically, and use this index for all calls to Make.
  30. */
  31. static int NewIndex() {
  32. static std::atomic<int> nextIndex{0};
  33. return nextIndex++;
  34. }
  35. /**
  36. * Creates a new fragment processor from an SkSL source string and a struct of inputs to the
  37. * program. The input struct's type is derived from the 'in' variables in the SkSL source, so
  38. * e.g. the shader:
  39. *
  40. * in bool dither;
  41. * in float x;
  42. * in float y;
  43. * ....
  44. *
  45. * would expect a pointer to a struct set up like:
  46. *
  47. * struct {
  48. * bool dither;
  49. * float x;
  50. * float y;
  51. * };
  52. *
  53. * As turning SkSL into GLSL / SPIR-V / etc. is fairly expensive, and the output may differ
  54. * based on the inputs, internally the process is divided into two steps: we first parse and
  55. * semantically analyze the SkSL into an internal representation, and then "specialize" this
  56. * internal representation based on the inputs. The unspecialized internal representation of
  57. * the program is cached, so further specializations of the same code are much faster than the
  58. * first call.
  59. *
  60. * This caching is based on the 'index' parameter, which should be derived by statically calling
  61. * 'NewIndex()'. Each given SkSL string should have a single, statically defined index
  62. * associated with it.
  63. */
  64. static std::unique_ptr<GrSkSLFP> Make(
  65. GrContext_Base* context,
  66. int index,
  67. const char* name,
  68. const char* sksl,
  69. const void* inputs,
  70. size_t inputSize,
  71. SkSL::Program::Kind kind = SkSL::Program::kPipelineStage_Kind);
  72. static std::unique_ptr<GrSkSLFP> Make(
  73. GrContext_Base* context,
  74. int index,
  75. const char* name,
  76. SkString sksl,
  77. const void* inputs,
  78. size_t inputSize,
  79. SkSL::Program::Kind kind = SkSL::Program::kPipelineStage_Kind);
  80. const char* name() const override;
  81. void addChild(std::unique_ptr<GrFragmentProcessor> child);
  82. std::unique_ptr<GrFragmentProcessor> clone() const override;
  83. private:
  84. GrSkSLFP(sk_sp<GrSkSLFPFactoryCache> factoryCache, const GrShaderCaps* shaderCaps,
  85. SkSL::Program::Kind kind, int fIndex, const char* name, const char* sksl,
  86. SkString skslString, const void* inputs, size_t inputSize);
  87. GrSkSLFP(const GrSkSLFP& other);
  88. GrGLSLFragmentProcessor* onCreateGLSLInstance() const override;
  89. void onGetGLSLProcessorKey(const GrShaderCaps&, GrProcessorKeyBuilder*) const override;
  90. bool onIsEqual(const GrFragmentProcessor&) const override;
  91. void createFactory() const;
  92. sk_sp<GrSkSLFPFactoryCache> fFactoryCache;
  93. const sk_sp<GrShaderCaps> fShaderCaps;
  94. mutable sk_sp<GrSkSLFPFactory> fFactory;
  95. SkSL::Program::Kind fKind;
  96. int fIndex;
  97. const char* fName;
  98. // For object lifetime purposes, we have fields for the SkSL as both a const char* and a
  99. // SkString. The const char* is the one we actually use, but it may point to the SkString's
  100. // bytes. Since GrSkSLFPs are frequently created from constant strings, this allows us to
  101. // generally avoid the overhead of copying the bytes into an SkString (in which case fSkSLString
  102. // is the empty string), while still allowing the GrSkSLFP to manage the string's lifetime when
  103. // needed.
  104. SkString fSkSLString;
  105. const char* fSkSL;
  106. const std::unique_ptr<int8_t[]> fInputs;
  107. size_t fInputSize;
  108. mutable SkSL::String fKey;
  109. GR_DECLARE_FRAGMENT_PROCESSOR_TEST
  110. typedef GrFragmentProcessor INHERITED;
  111. friend class GrGLSLSkSLFP;
  112. friend class GrSkSLFPFactory;
  113. };
  114. /**
  115. * Produces GrFragmentProcessors from SkSL code. As the shader code produced from the SkSL depends
  116. * upon the inputs to the SkSL (static if's, etc.) we first create a factory for a given SkSL
  117. * string, then use that to create the actual GrFragmentProcessor.
  118. */
  119. class GrSkSLFPFactory : public SkNVRefCnt<GrSkSLFPFactory> {
  120. public:
  121. /**
  122. * Constructs a GrSkSLFPFactory for a given SkSL source string. Creating a factory will
  123. * preprocess the SkSL and determine which of its inputs are declared "key" (meaning they cause
  124. * the produced shaders to differ), so it is important to reuse the same factory instance for
  125. * the same shader in order to avoid repeatedly re-parsing the SkSL.
  126. */
  127. GrSkSLFPFactory(const char* name, const GrShaderCaps* shaderCaps, const char* sksl,
  128. SkSL::Program::Kind kind = SkSL::Program::kPipelineStage_Kind);
  129. const SkSL::Program* getSpecialization(const SkSL::String& key, const void* inputs,
  130. size_t inputSize);
  131. SkSL::Program::Kind fKind;
  132. const char* fName;
  133. SkSL::Compiler fCompiler;
  134. std::shared_ptr<SkSL::Program> fBaseProgram;
  135. std::vector<const SkSL::Variable*> fInputVars;
  136. std::vector<const SkSL::Variable*> fKeyVars;
  137. std::unordered_map<SkSL::String, std::unique_ptr<const SkSL::Program>> fSpecializations;
  138. friend class GrSkSLFP;
  139. };
  140. #endif