xref: /aosp_15_r20/external/skia/bench/SkSLBench.cpp (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
1*c8dee2aaSAndroid Build Coastguard Worker /*
2*c8dee2aaSAndroid Build Coastguard Worker  * Copyright 2019 Google LLC
3*c8dee2aaSAndroid Build Coastguard Worker  *
4*c8dee2aaSAndroid Build Coastguard Worker  * Use of this source code is governed by a BSD-style license that can be
5*c8dee2aaSAndroid Build Coastguard Worker  * found in the LICENSE file.
6*c8dee2aaSAndroid Build Coastguard Worker  */
7*c8dee2aaSAndroid Build Coastguard Worker #include "bench/Benchmark.h"
8*c8dee2aaSAndroid Build Coastguard Worker #include "bench/ResultsWriter.h"
9*c8dee2aaSAndroid Build Coastguard Worker #include "bench/SkSLBench.h"
10*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkCanvas.h"
11*c8dee2aaSAndroid Build Coastguard Worker #include "src/base/SkArenaAlloc.h"
12*c8dee2aaSAndroid Build Coastguard Worker #include "src/core/SkRasterPipeline.h"
13*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/GrCaps.h"
14*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/GrRecordingContextPriv.h"
15*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/mock/GrMockCaps.h"
16*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/SkSLCompiler.h"
17*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/SkSLModuleLoader.h"
18*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/SkSLParser.h"
19*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/codegen/SkSLGLSLCodeGenerator.h"
20*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/codegen/SkSLMetalCodeGenerator.h"
21*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/codegen/SkSLRasterPipelineBuilder.h"
22*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/codegen/SkSLRasterPipelineCodeGenerator.h"
23*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/codegen/SkSLSPIRVCodeGenerator.h"
24*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/codegen/SkSLWGSLCodeGenerator.h"
25*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/ir/SkSLFunctionDeclaration.h"
26*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/ir/SkSLProgram.h"
27*c8dee2aaSAndroid Build Coastguard Worker 
28*c8dee2aaSAndroid Build Coastguard Worker #include <regex>
29*c8dee2aaSAndroid Build Coastguard Worker 
30*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_shared.minified.sksl"
31*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_compute.minified.sksl"
32*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_frag.minified.sksl"
33*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_gpu.minified.sksl"
34*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_public.minified.sksl"
35*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_rt_shader.minified.sksl"
36*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_vert.minified.sksl"
37*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_graphite_frag.minified.sksl"
38*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_graphite_vert.minified.sksl"
39*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_graphite_frag_es2.minified.sksl"
40*c8dee2aaSAndroid Build Coastguard Worker #include "src/sksl/generated/sksl_graphite_vert_es2.minified.sksl"
41*c8dee2aaSAndroid Build Coastguard Worker 
42*c8dee2aaSAndroid Build Coastguard Worker class SkSLCompilerStartupBench : public Benchmark {
43*c8dee2aaSAndroid Build Coastguard Worker protected:
onGetName()44*c8dee2aaSAndroid Build Coastguard Worker     const char* onGetName() override {
45*c8dee2aaSAndroid Build Coastguard Worker         return "sksl_compiler_startup";
46*c8dee2aaSAndroid Build Coastguard Worker     }
47*c8dee2aaSAndroid Build Coastguard Worker 
isSuitableFor(Backend backend)48*c8dee2aaSAndroid Build Coastguard Worker     bool isSuitableFor(Backend backend) override {
49*c8dee2aaSAndroid Build Coastguard Worker         return backend == Backend::kNonRendering;
50*c8dee2aaSAndroid Build Coastguard Worker     }
51*c8dee2aaSAndroid Build Coastguard Worker 
onDraw(int loops,SkCanvas *)52*c8dee2aaSAndroid Build Coastguard Worker     void onDraw(int loops, SkCanvas*) override {
53*c8dee2aaSAndroid Build Coastguard Worker         for (int i = 0; i < loops; i++) {
54*c8dee2aaSAndroid Build Coastguard Worker             SkSL::Compiler compiler;
55*c8dee2aaSAndroid Build Coastguard Worker         }
56*c8dee2aaSAndroid Build Coastguard Worker     }
57*c8dee2aaSAndroid Build Coastguard Worker };
58*c8dee2aaSAndroid Build Coastguard Worker 
59*c8dee2aaSAndroid Build Coastguard Worker DEF_BENCH(return new SkSLCompilerStartupBench();)
60*c8dee2aaSAndroid Build Coastguard Worker 
61*c8dee2aaSAndroid Build Coastguard Worker enum class Output {
62*c8dee2aaSAndroid Build Coastguard Worker     kNone,
63*c8dee2aaSAndroid Build Coastguard Worker     kGLSL,
64*c8dee2aaSAndroid Build Coastguard Worker     kMetal,
65*c8dee2aaSAndroid Build Coastguard Worker     kSPIRV,
66*c8dee2aaSAndroid Build Coastguard Worker     kSkRP,
67*c8dee2aaSAndroid Build Coastguard Worker     kGrMtl,
68*c8dee2aaSAndroid Build Coastguard Worker     kGrWGSL,
69*c8dee2aaSAndroid Build Coastguard Worker };
70*c8dee2aaSAndroid Build Coastguard Worker 
71*c8dee2aaSAndroid Build Coastguard Worker class SkSLCompileBench : public Benchmark {
72*c8dee2aaSAndroid Build Coastguard Worker public:
output_string(Output output)73*c8dee2aaSAndroid Build Coastguard Worker     static const char* output_string(Output output) {
74*c8dee2aaSAndroid Build Coastguard Worker         switch (output) {
75*c8dee2aaSAndroid Build Coastguard Worker             case Output::kNone:    return "";
76*c8dee2aaSAndroid Build Coastguard Worker             case Output::kGLSL:    return "glsl_";
77*c8dee2aaSAndroid Build Coastguard Worker             case Output::kMetal:   return "metal_";
78*c8dee2aaSAndroid Build Coastguard Worker             case Output::kSPIRV:   return "spirv_";
79*c8dee2aaSAndroid Build Coastguard Worker             case Output::kGrMtl:   return "grmtl_";
80*c8dee2aaSAndroid Build Coastguard Worker             case Output::kGrWGSL:  return "grwgsl_";
81*c8dee2aaSAndroid Build Coastguard Worker             case Output::kSkRP:    return "skrp_";
82*c8dee2aaSAndroid Build Coastguard Worker         }
83*c8dee2aaSAndroid Build Coastguard Worker         SkUNREACHABLE;
84*c8dee2aaSAndroid Build Coastguard Worker     }
85*c8dee2aaSAndroid Build Coastguard Worker 
SkSLCompileBench(std::string name,const char * src,bool optimize,Output output)86*c8dee2aaSAndroid Build Coastguard Worker     SkSLCompileBench(std::string name, const char* src, bool optimize, Output output)
87*c8dee2aaSAndroid Build Coastguard Worker             : fName(std::string("sksl_") + (optimize ? "" : "unoptimized_") +
88*c8dee2aaSAndroid Build Coastguard Worker                     output_string(output) + name)
89*c8dee2aaSAndroid Build Coastguard Worker             , fSrc(src)
90*c8dee2aaSAndroid Build Coastguard Worker             , fCaps(GrContextOptions(), GrMockOptions())
91*c8dee2aaSAndroid Build Coastguard Worker             , fOutput(output) {
92*c8dee2aaSAndroid Build Coastguard Worker         fSettings.fOptimize = optimize;
93*c8dee2aaSAndroid Build Coastguard Worker         // The test programs we compile don't follow Vulkan rules and thus produce invalid SPIR-V.
94*c8dee2aaSAndroid Build Coastguard Worker         // This is harmless, so long as we don't try to validate them.
95*c8dee2aaSAndroid Build Coastguard Worker         fSettings.fValidateSPIRV = false;
96*c8dee2aaSAndroid Build Coastguard Worker 
97*c8dee2aaSAndroid Build Coastguard Worker         this->fixUpSource();
98*c8dee2aaSAndroid Build Coastguard Worker     }
99*c8dee2aaSAndroid Build Coastguard Worker 
100*c8dee2aaSAndroid Build Coastguard Worker protected:
onGetName()101*c8dee2aaSAndroid Build Coastguard Worker     const char* onGetName() override {
102*c8dee2aaSAndroid Build Coastguard Worker         return fName.c_str();
103*c8dee2aaSAndroid Build Coastguard Worker     }
104*c8dee2aaSAndroid Build Coastguard Worker 
isSuitableFor(Backend backend)105*c8dee2aaSAndroid Build Coastguard Worker     bool isSuitableFor(Backend backend) override {
106*c8dee2aaSAndroid Build Coastguard Worker #if !defined(SK_GRAPHITE)
107*c8dee2aaSAndroid Build Coastguard Worker         if (this->usesGraphite()) {
108*c8dee2aaSAndroid Build Coastguard Worker             return false;
109*c8dee2aaSAndroid Build Coastguard Worker         }
110*c8dee2aaSAndroid Build Coastguard Worker #endif
111*c8dee2aaSAndroid Build Coastguard Worker         return backend == Backend::kNonRendering;
112*c8dee2aaSAndroid Build Coastguard Worker     }
113*c8dee2aaSAndroid Build Coastguard Worker 
usesRuntimeShader() const114*c8dee2aaSAndroid Build Coastguard Worker     bool usesRuntimeShader() const {
115*c8dee2aaSAndroid Build Coastguard Worker         return fOutput == Output::kSkRP;
116*c8dee2aaSAndroid Build Coastguard Worker     }
117*c8dee2aaSAndroid Build Coastguard Worker 
usesGraphite() const118*c8dee2aaSAndroid Build Coastguard Worker     bool usesGraphite() const {
119*c8dee2aaSAndroid Build Coastguard Worker         return fOutput == Output::kGrMtl || fOutput == Output::kGrWGSL;
120*c8dee2aaSAndroid Build Coastguard Worker     }
121*c8dee2aaSAndroid Build Coastguard Worker 
fixUpSource()122*c8dee2aaSAndroid Build Coastguard Worker     void fixUpSource() {
123*c8dee2aaSAndroid Build Coastguard Worker         auto fixup = [this](const char* input, const char* replacement) {
124*c8dee2aaSAndroid Build Coastguard Worker             fSrc = std::regex_replace(fSrc, std::regex(input), replacement);
125*c8dee2aaSAndroid Build Coastguard Worker         };
126*c8dee2aaSAndroid Build Coastguard Worker 
127*c8dee2aaSAndroid Build Coastguard Worker         // Runtime shaders have slightly different conventions than fragment shaders.
128*c8dee2aaSAndroid Build Coastguard Worker         // Perform a handful of fixups to compensate. These are hand-tuned for our current set of
129*c8dee2aaSAndroid Build Coastguard Worker         // test shaders and will probably need to be updated if we add more.
130*c8dee2aaSAndroid Build Coastguard Worker         if (this->usesRuntimeShader()) {
131*c8dee2aaSAndroid Build Coastguard Worker             fixup(R"(void main\(\))",                              "half4 main(float2 xy)");
132*c8dee2aaSAndroid Build Coastguard Worker             fixup(R"(sk_FragColor =)",                             "return");
133*c8dee2aaSAndroid Build Coastguard Worker             fixup(R"(sk_FragCoord)",                               "_FragCoord");
134*c8dee2aaSAndroid Build Coastguard Worker             fixup(R"(sampler2D )",                                 "uniform shader ");
135*c8dee2aaSAndroid Build Coastguard Worker             fixup(R"((flat |noperspective |)in )",                 "uniform ");
136*c8dee2aaSAndroid Build Coastguard Worker             fixup(R"(sample\(([A-Za-z0-9_]+), ([A-Za-z0-9_]+)\))", "$01.eval($02)");
137*c8dee2aaSAndroid Build Coastguard Worker             fSrc = "#version 300\nuniform float4 _FragCoord;\n" + fSrc;
138*c8dee2aaSAndroid Build Coastguard Worker         }
139*c8dee2aaSAndroid Build Coastguard Worker     }
140*c8dee2aaSAndroid Build Coastguard Worker 
onDraw(int loops,SkCanvas * canvas)141*c8dee2aaSAndroid Build Coastguard Worker     void onDraw(int loops, SkCanvas* canvas) override {
142*c8dee2aaSAndroid Build Coastguard Worker         SkSL::ProgramKind kind;
143*c8dee2aaSAndroid Build Coastguard Worker         if (this->usesRuntimeShader()) {
144*c8dee2aaSAndroid Build Coastguard Worker             kind = SkSL::ProgramKind::kRuntimeShader;
145*c8dee2aaSAndroid Build Coastguard Worker         } else if (this->usesGraphite()) {
146*c8dee2aaSAndroid Build Coastguard Worker             kind = SkSL::ProgramKind::kGraphiteFragment;
147*c8dee2aaSAndroid Build Coastguard Worker         } else {
148*c8dee2aaSAndroid Build Coastguard Worker             kind = SkSL::ProgramKind::kFragment;
149*c8dee2aaSAndroid Build Coastguard Worker         }
150*c8dee2aaSAndroid Build Coastguard Worker         for (int i = 0; i < loops; i++) {
151*c8dee2aaSAndroid Build Coastguard Worker             std::unique_ptr<SkSL::Program> program = fCompiler.convertProgram(kind, fSrc,
152*c8dee2aaSAndroid Build Coastguard Worker                                                                               fSettings);
153*c8dee2aaSAndroid Build Coastguard Worker             if (fCompiler.errorCount()) {
154*c8dee2aaSAndroid Build Coastguard Worker                 SK_ABORT("shader compilation failed: %s\n", fCompiler.errorText().c_str());
155*c8dee2aaSAndroid Build Coastguard Worker             }
156*c8dee2aaSAndroid Build Coastguard Worker             std::string result;
157*c8dee2aaSAndroid Build Coastguard Worker             switch (fOutput) {
158*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kNone:
159*c8dee2aaSAndroid Build Coastguard Worker                     break;
160*c8dee2aaSAndroid Build Coastguard Worker 
161*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kGLSL:
162*c8dee2aaSAndroid Build Coastguard Worker                     SkAssertResult(SkSL::ToGLSL(*program, fCaps.shaderCaps(), &result));
163*c8dee2aaSAndroid Build Coastguard Worker                     break;
164*c8dee2aaSAndroid Build Coastguard Worker 
165*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kMetal:
166*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kGrMtl:
167*c8dee2aaSAndroid Build Coastguard Worker                     SkAssertResult(SkSL::ToMetal(*program, fCaps.shaderCaps(), &result));
168*c8dee2aaSAndroid Build Coastguard Worker                     break;
169*c8dee2aaSAndroid Build Coastguard Worker 
170*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kSPIRV:
171*c8dee2aaSAndroid Build Coastguard Worker                     SkAssertResult(SkSL::ToSPIRV(*program, fCaps.shaderCaps(), &result));
172*c8dee2aaSAndroid Build Coastguard Worker                     break;
173*c8dee2aaSAndroid Build Coastguard Worker 
174*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kGrWGSL:
175*c8dee2aaSAndroid Build Coastguard Worker                     SkAssertResult(SkSL::ToWGSL(*program, fCaps.shaderCaps(), &result));
176*c8dee2aaSAndroid Build Coastguard Worker                     break;
177*c8dee2aaSAndroid Build Coastguard Worker 
178*c8dee2aaSAndroid Build Coastguard Worker                 case Output::kSkRP:
179*c8dee2aaSAndroid Build Coastguard Worker                     SkAssertResult(CompileToSkRP(*program));
180*c8dee2aaSAndroid Build Coastguard Worker                     break;
181*c8dee2aaSAndroid Build Coastguard Worker             }
182*c8dee2aaSAndroid Build Coastguard Worker         }
183*c8dee2aaSAndroid Build Coastguard Worker     }
184*c8dee2aaSAndroid Build Coastguard Worker 
CompileToSkRP(const SkSL::Program & program)185*c8dee2aaSAndroid Build Coastguard Worker     static bool CompileToSkRP(const SkSL::Program& program) {
186*c8dee2aaSAndroid Build Coastguard Worker         const SkSL::FunctionDeclaration* main = program.getFunction("main");
187*c8dee2aaSAndroid Build Coastguard Worker         if (!main) {
188*c8dee2aaSAndroid Build Coastguard Worker             return false;
189*c8dee2aaSAndroid Build Coastguard Worker         }
190*c8dee2aaSAndroid Build Coastguard Worker 
191*c8dee2aaSAndroid Build Coastguard Worker         // Compile our program.
192*c8dee2aaSAndroid Build Coastguard Worker         std::unique_ptr<SkSL::RP::Program> rasterProg = SkSL::MakeRasterPipelineProgram(
193*c8dee2aaSAndroid Build Coastguard Worker                 program, *main->definition(), /*debugTrace=*/nullptr, /*writeTraceOps=*/false);
194*c8dee2aaSAndroid Build Coastguard Worker         if (!rasterProg) {
195*c8dee2aaSAndroid Build Coastguard Worker             return false;
196*c8dee2aaSAndroid Build Coastguard Worker         }
197*c8dee2aaSAndroid Build Coastguard Worker 
198*c8dee2aaSAndroid Build Coastguard Worker         // We need to supply a valid uniform range, but the uniform values inside don't actually
199*c8dee2aaSAndroid Build Coastguard Worker         // matter, since we aren't going to run the shader.
200*c8dee2aaSAndroid Build Coastguard Worker         float uniformBuffer[1024];
201*c8dee2aaSAndroid Build Coastguard Worker         if (rasterProg->numUniforms() > (int)std::size(uniformBuffer)) {
202*c8dee2aaSAndroid Build Coastguard Worker             return false;
203*c8dee2aaSAndroid Build Coastguard Worker         }
204*c8dee2aaSAndroid Build Coastguard Worker 
205*c8dee2aaSAndroid Build Coastguard Worker         // Append the program to a raster pipeline.
206*c8dee2aaSAndroid Build Coastguard Worker         SkSTArenaAlloc<2048> alloc;
207*c8dee2aaSAndroid Build Coastguard Worker         SkRasterPipeline pipeline(&alloc);
208*c8dee2aaSAndroid Build Coastguard Worker         rasterProg->appendStages(&pipeline,
209*c8dee2aaSAndroid Build Coastguard Worker                                  &alloc,
210*c8dee2aaSAndroid Build Coastguard Worker                                  /*callbacks=*/nullptr,
211*c8dee2aaSAndroid Build Coastguard Worker                                  /*uniforms=*/SkSpan{uniformBuffer, rasterProg->numUniforms()});
212*c8dee2aaSAndroid Build Coastguard Worker         return true;
213*c8dee2aaSAndroid Build Coastguard Worker     }
214*c8dee2aaSAndroid Build Coastguard Worker 
215*c8dee2aaSAndroid Build Coastguard Worker private:
216*c8dee2aaSAndroid Build Coastguard Worker     std::string fName;
217*c8dee2aaSAndroid Build Coastguard Worker     std::string fSrc;
218*c8dee2aaSAndroid Build Coastguard Worker     GrMockCaps fCaps;
219*c8dee2aaSAndroid Build Coastguard Worker     SkSL::Compiler fCompiler;
220*c8dee2aaSAndroid Build Coastguard Worker     SkSL::ProgramSettings fSettings;
221*c8dee2aaSAndroid Build Coastguard Worker     Output fOutput;
222*c8dee2aaSAndroid Build Coastguard Worker 
223*c8dee2aaSAndroid Build Coastguard Worker     using INHERITED = Benchmark;
224*c8dee2aaSAndroid Build Coastguard Worker };
225*c8dee2aaSAndroid Build Coastguard Worker 
226*c8dee2aaSAndroid Build Coastguard Worker ///////////////////////////////////////////////////////////////////////////////
227*c8dee2aaSAndroid Build Coastguard Worker 
228*c8dee2aaSAndroid Build Coastguard Worker #define COMPILER_BENCH(name, text)                                                               \
229*c8dee2aaSAndroid Build Coastguard Worker   static constexpr char name ## _SRC[] = text;                                                   \
230*c8dee2aaSAndroid Build Coastguard Worker   DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/false, Output::kNone);)  \
231*c8dee2aaSAndroid Build Coastguard Worker   DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true,  Output::kNone);)  \
232*c8dee2aaSAndroid Build Coastguard Worker   DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true,  Output::kGLSL);)  \
233*c8dee2aaSAndroid Build Coastguard Worker   DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true,  Output::kMetal);) \
234*c8dee2aaSAndroid Build Coastguard Worker   DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true,  Output::kSPIRV);) \
235*c8dee2aaSAndroid Build Coastguard Worker   DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true,  Output::kSkRP);)
236*c8dee2aaSAndroid Build Coastguard Worker 
237*c8dee2aaSAndroid Build Coastguard Worker // This fragment shader is from the third tile on the top row of GM_gradients_2pt_conical_outside.
238*c8dee2aaSAndroid Build Coastguard Worker // To get an ES2 compatible shader, nonconstantArrayIndexSupport in GrShaderCaps is forced off.
239*c8dee2aaSAndroid Build Coastguard Worker COMPILER_BENCH(large, R"(
240*c8dee2aaSAndroid Build Coastguard Worker uniform half4 uthresholds1_7_S1_c0_c0_c0;
241*c8dee2aaSAndroid Build Coastguard Worker uniform half4 uthresholds9_13_S1_c0_c0_c0;
242*c8dee2aaSAndroid Build Coastguard Worker uniform float4 uscale_S1_c0_c0_c0[4];
243*c8dee2aaSAndroid Build Coastguard Worker uniform float4 ubias_S1_c0_c0_c0[4];
244*c8dee2aaSAndroid Build Coastguard Worker uniform half uinvR1_S1_c0_c0_c1_c0;
245*c8dee2aaSAndroid Build Coastguard Worker uniform half ufx_S1_c0_c0_c1_c0;
246*c8dee2aaSAndroid Build Coastguard Worker uniform float3x3 umatrix_S1_c0_c0_c1;
247*c8dee2aaSAndroid Build Coastguard Worker uniform half4 uleftBorderColor_S1_c0_c0;
248*c8dee2aaSAndroid Build Coastguard Worker uniform half4 urightBorderColor_S1_c0_c0;
249*c8dee2aaSAndroid Build Coastguard Worker uniform float3x3 umatrix_S1_c1;
250*c8dee2aaSAndroid Build Coastguard Worker uniform half urange_S1;
251*c8dee2aaSAndroid Build Coastguard Worker sampler2D uTextureSampler_0_S1;
252*c8dee2aaSAndroid Build Coastguard Worker flat in half4 vcolor_S0;
253*c8dee2aaSAndroid Build Coastguard Worker noperspective in float2 vTransformedCoords_6_S0;
254*c8dee2aaSAndroid Build Coastguard Worker half4 UnrolledBinaryColorizer_S1_c0_c0_c0(half4 _input, float2 _coords)
255*c8dee2aaSAndroid Build Coastguard Worker {
256*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_0_inColor = _input;
257*c8dee2aaSAndroid Build Coastguard Worker 	float2 _tmp_1_coords = _coords;
258*c8dee2aaSAndroid Build Coastguard Worker 	half t = half(_tmp_1_coords.x);
259*c8dee2aaSAndroid Build Coastguard Worker 	float4 s;
260*c8dee2aaSAndroid Build Coastguard Worker 	float4 b;
261*c8dee2aaSAndroid Build Coastguard Worker 	{
262*c8dee2aaSAndroid Build Coastguard Worker 		if (t < uthresholds1_7_S1_c0_c0_c0.y)
263*c8dee2aaSAndroid Build Coastguard Worker 		{
264*c8dee2aaSAndroid Build Coastguard Worker 			if (t < uthresholds1_7_S1_c0_c0_c0.x)
265*c8dee2aaSAndroid Build Coastguard Worker 			{
266*c8dee2aaSAndroid Build Coastguard Worker 				s = uscale_S1_c0_c0_c0[0];
267*c8dee2aaSAndroid Build Coastguard Worker 				b = ubias_S1_c0_c0_c0[0];
268*c8dee2aaSAndroid Build Coastguard Worker 			}
269*c8dee2aaSAndroid Build Coastguard Worker 			else
270*c8dee2aaSAndroid Build Coastguard Worker 			{
271*c8dee2aaSAndroid Build Coastguard Worker 				s = uscale_S1_c0_c0_c0[1];
272*c8dee2aaSAndroid Build Coastguard Worker 				b = ubias_S1_c0_c0_c0[1];
273*c8dee2aaSAndroid Build Coastguard Worker 			}
274*c8dee2aaSAndroid Build Coastguard Worker 		}
275*c8dee2aaSAndroid Build Coastguard Worker 		else
276*c8dee2aaSAndroid Build Coastguard Worker 		{
277*c8dee2aaSAndroid Build Coastguard Worker 			if (t < uthresholds1_7_S1_c0_c0_c0.z)
278*c8dee2aaSAndroid Build Coastguard Worker 			{
279*c8dee2aaSAndroid Build Coastguard Worker 				s = uscale_S1_c0_c0_c0[2];
280*c8dee2aaSAndroid Build Coastguard Worker 				b = ubias_S1_c0_c0_c0[2];
281*c8dee2aaSAndroid Build Coastguard Worker 			}
282*c8dee2aaSAndroid Build Coastguard Worker 			else
283*c8dee2aaSAndroid Build Coastguard Worker 			{
284*c8dee2aaSAndroid Build Coastguard Worker 				s = uscale_S1_c0_c0_c0[3];
285*c8dee2aaSAndroid Build Coastguard Worker 				b = ubias_S1_c0_c0_c0[3];
286*c8dee2aaSAndroid Build Coastguard Worker 			}
287*c8dee2aaSAndroid Build Coastguard Worker 		}
288*c8dee2aaSAndroid Build Coastguard Worker 	}
289*c8dee2aaSAndroid Build Coastguard Worker 	return half4(half4(float(t) * s + b));
290*c8dee2aaSAndroid Build Coastguard Worker }
291*c8dee2aaSAndroid Build Coastguard Worker half4 TwoPointConicalFocalLayout_S1_c0_c0_c1_c0(half4 _input)
292*c8dee2aaSAndroid Build Coastguard Worker {
293*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_2_inColor = _input;
294*c8dee2aaSAndroid Build Coastguard Worker 	float2 _tmp_3_coords = vTransformedCoords_6_S0;
295*c8dee2aaSAndroid Build Coastguard Worker 	float t = -1.0;
296*c8dee2aaSAndroid Build Coastguard Worker 	half v = 1.0;
297*c8dee2aaSAndroid Build Coastguard Worker 	float x_t = -1.0;
298*c8dee2aaSAndroid Build Coastguard Worker 	if (bool(int(0)))
299*c8dee2aaSAndroid Build Coastguard Worker 	{
300*c8dee2aaSAndroid Build Coastguard Worker 		x_t = dot(_tmp_3_coords, _tmp_3_coords) / _tmp_3_coords.x;
301*c8dee2aaSAndroid Build Coastguard Worker 	}
302*c8dee2aaSAndroid Build Coastguard Worker 	else if (bool(int(0)))
303*c8dee2aaSAndroid Build Coastguard Worker 	{
304*c8dee2aaSAndroid Build Coastguard Worker 		x_t = length(_tmp_3_coords) - _tmp_3_coords.x * float(uinvR1_S1_c0_c0_c1_c0);
305*c8dee2aaSAndroid Build Coastguard Worker 	}
306*c8dee2aaSAndroid Build Coastguard Worker 	else
307*c8dee2aaSAndroid Build Coastguard Worker 	{
308*c8dee2aaSAndroid Build Coastguard Worker 		float temp = _tmp_3_coords.x * _tmp_3_coords.x - _tmp_3_coords.y * _tmp_3_coords.y;
309*c8dee2aaSAndroid Build Coastguard Worker 		if (temp >= 0.0)
310*c8dee2aaSAndroid Build Coastguard Worker 		{
311*c8dee2aaSAndroid Build Coastguard Worker 			if (bool(int(0)) || !bool(int(1)))
312*c8dee2aaSAndroid Build Coastguard Worker 			{
313*c8dee2aaSAndroid Build Coastguard Worker 				x_t = -sqrt(temp) - _tmp_3_coords.x * float(uinvR1_S1_c0_c0_c1_c0);
314*c8dee2aaSAndroid Build Coastguard Worker 			}
315*c8dee2aaSAndroid Build Coastguard Worker 			else
316*c8dee2aaSAndroid Build Coastguard Worker 			{
317*c8dee2aaSAndroid Build Coastguard Worker 				x_t = sqrt(temp) - _tmp_3_coords.x * float(uinvR1_S1_c0_c0_c1_c0);
318*c8dee2aaSAndroid Build Coastguard Worker 			}
319*c8dee2aaSAndroid Build Coastguard Worker 		}
320*c8dee2aaSAndroid Build Coastguard Worker 	}
321*c8dee2aaSAndroid Build Coastguard Worker 	if (!bool(int(0)))
322*c8dee2aaSAndroid Build Coastguard Worker 	{
323*c8dee2aaSAndroid Build Coastguard Worker 		if (x_t <= 0.0)
324*c8dee2aaSAndroid Build Coastguard Worker 		{
325*c8dee2aaSAndroid Build Coastguard Worker 			v = -1.0;
326*c8dee2aaSAndroid Build Coastguard Worker 		}
327*c8dee2aaSAndroid Build Coastguard Worker 	}
328*c8dee2aaSAndroid Build Coastguard Worker 	if (bool(int(1)))
329*c8dee2aaSAndroid Build Coastguard Worker 	{
330*c8dee2aaSAndroid Build Coastguard Worker 		if (bool(int(0)))
331*c8dee2aaSAndroid Build Coastguard Worker 		{
332*c8dee2aaSAndroid Build Coastguard Worker 			t = x_t;
333*c8dee2aaSAndroid Build Coastguard Worker 		}
334*c8dee2aaSAndroid Build Coastguard Worker 		else
335*c8dee2aaSAndroid Build Coastguard Worker 		{
336*c8dee2aaSAndroid Build Coastguard Worker 			t = x_t + float(ufx_S1_c0_c0_c1_c0);
337*c8dee2aaSAndroid Build Coastguard Worker 		}
338*c8dee2aaSAndroid Build Coastguard Worker 	}
339*c8dee2aaSAndroid Build Coastguard Worker 	else
340*c8dee2aaSAndroid Build Coastguard Worker 	{
341*c8dee2aaSAndroid Build Coastguard Worker 		if (bool(int(0)))
342*c8dee2aaSAndroid Build Coastguard Worker 		{
343*c8dee2aaSAndroid Build Coastguard Worker 			t = -x_t;
344*c8dee2aaSAndroid Build Coastguard Worker 		}
345*c8dee2aaSAndroid Build Coastguard Worker 		else
346*c8dee2aaSAndroid Build Coastguard Worker 		{
347*c8dee2aaSAndroid Build Coastguard Worker 			t = -x_t + float(ufx_S1_c0_c0_c1_c0);
348*c8dee2aaSAndroid Build Coastguard Worker 		}
349*c8dee2aaSAndroid Build Coastguard Worker 	}
350*c8dee2aaSAndroid Build Coastguard Worker 	if (bool(int(0)))
351*c8dee2aaSAndroid Build Coastguard Worker 	{
352*c8dee2aaSAndroid Build Coastguard Worker 		t = 1.0 - t;
353*c8dee2aaSAndroid Build Coastguard Worker 	}
354*c8dee2aaSAndroid Build Coastguard Worker 	return half4(half4(half(t), v, 0.0, 0.0));
355*c8dee2aaSAndroid Build Coastguard Worker }
356*c8dee2aaSAndroid Build Coastguard Worker half4 MatrixEffect_S1_c0_c0_c1(half4 _input)
357*c8dee2aaSAndroid Build Coastguard Worker {
358*c8dee2aaSAndroid Build Coastguard Worker 	return TwoPointConicalFocalLayout_S1_c0_c0_c1_c0(_input);
359*c8dee2aaSAndroid Build Coastguard Worker }
360*c8dee2aaSAndroid Build Coastguard Worker half4 ClampedGradient_S1_c0_c0(half4 _input)
361*c8dee2aaSAndroid Build Coastguard Worker {
362*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_4_inColor = _input;
363*c8dee2aaSAndroid Build Coastguard Worker 	half4 t = MatrixEffect_S1_c0_c0_c1(_tmp_4_inColor);
364*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor;
365*c8dee2aaSAndroid Build Coastguard Worker 	if (!bool(int(0)) && t.y < 0.0)
366*c8dee2aaSAndroid Build Coastguard Worker 	{
367*c8dee2aaSAndroid Build Coastguard Worker 		outColor = half4(0.0);
368*c8dee2aaSAndroid Build Coastguard Worker 	}
369*c8dee2aaSAndroid Build Coastguard Worker 	else if (t.x < 0.0)
370*c8dee2aaSAndroid Build Coastguard Worker 	{
371*c8dee2aaSAndroid Build Coastguard Worker 		outColor = uleftBorderColor_S1_c0_c0;
372*c8dee2aaSAndroid Build Coastguard Worker 	}
373*c8dee2aaSAndroid Build Coastguard Worker 	else if (t.x > 1.0)
374*c8dee2aaSAndroid Build Coastguard Worker 	{
375*c8dee2aaSAndroid Build Coastguard Worker 		outColor = urightBorderColor_S1_c0_c0;
376*c8dee2aaSAndroid Build Coastguard Worker 	}
377*c8dee2aaSAndroid Build Coastguard Worker 	else
378*c8dee2aaSAndroid Build Coastguard Worker 	{
379*c8dee2aaSAndroid Build Coastguard Worker 		outColor = UnrolledBinaryColorizer_S1_c0_c0_c0(_tmp_4_inColor, float2(half2(t.x, 0.0)));
380*c8dee2aaSAndroid Build Coastguard Worker 	}
381*c8dee2aaSAndroid Build Coastguard Worker 	return half4(outColor);
382*c8dee2aaSAndroid Build Coastguard Worker }
383*c8dee2aaSAndroid Build Coastguard Worker half4 DisableCoverageAsAlpha_S1_c0(half4 _input)
384*c8dee2aaSAndroid Build Coastguard Worker {
385*c8dee2aaSAndroid Build Coastguard Worker 	_input = ClampedGradient_S1_c0_c0(_input);
386*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_5_inColor = _input;
387*c8dee2aaSAndroid Build Coastguard Worker 	return half4(_input);
388*c8dee2aaSAndroid Build Coastguard Worker }
389*c8dee2aaSAndroid Build Coastguard Worker half4 TextureEffect_S1_c1_c0(half4 _input, float2 _coords)
390*c8dee2aaSAndroid Build Coastguard Worker {
391*c8dee2aaSAndroid Build Coastguard Worker 	return sample(uTextureSampler_0_S1, _coords).000r;
392*c8dee2aaSAndroid Build Coastguard Worker }
393*c8dee2aaSAndroid Build Coastguard Worker half4 MatrixEffect_S1_c1(half4 _input, float2 _coords)
394*c8dee2aaSAndroid Build Coastguard Worker {
395*c8dee2aaSAndroid Build Coastguard Worker 	return TextureEffect_S1_c1_c0(_input, float3x2(umatrix_S1_c1) * _coords.xy1);
396*c8dee2aaSAndroid Build Coastguard Worker }
397*c8dee2aaSAndroid Build Coastguard Worker half4 Dither_S1(half4 _input)
398*c8dee2aaSAndroid Build Coastguard Worker {
399*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_6_inColor = _input;
400*c8dee2aaSAndroid Build Coastguard Worker 	half4 color = DisableCoverageAsAlpha_S1_c0(_tmp_6_inColor);
401*c8dee2aaSAndroid Build Coastguard Worker 	half value = MatrixEffect_S1_c1(_tmp_6_inColor, sk_FragCoord.xy).w - 0.5;
402*c8dee2aaSAndroid Build Coastguard Worker 	return half4(half4(clamp(color.xyz + value * urange_S1, 0.0, color.w), color.w));
403*c8dee2aaSAndroid Build Coastguard Worker }
404*c8dee2aaSAndroid Build Coastguard Worker void main()
405*c8dee2aaSAndroid Build Coastguard Worker {
406*c8dee2aaSAndroid Build Coastguard Worker 	// Stage 0, QuadPerEdgeAAGeometryProcessor
407*c8dee2aaSAndroid Build Coastguard Worker 	half4 outputColor_S0;
408*c8dee2aaSAndroid Build Coastguard Worker 	outputColor_S0 = vcolor_S0;
409*c8dee2aaSAndroid Build Coastguard Worker 	const half4 outputCoverage_S0 = half4(1);
410*c8dee2aaSAndroid Build Coastguard Worker 	half4 output_S1;
411*c8dee2aaSAndroid Build Coastguard Worker 	output_S1 = Dither_S1(outputColor_S0);
412*c8dee2aaSAndroid Build Coastguard Worker 	{
413*c8dee2aaSAndroid Build Coastguard Worker 		// Xfer Processor: Porter Duff
414*c8dee2aaSAndroid Build Coastguard Worker 		sk_FragColor = output_S1 * outputCoverage_S0;
415*c8dee2aaSAndroid Build Coastguard Worker 	}
416*c8dee2aaSAndroid Build Coastguard Worker }
417*c8dee2aaSAndroid Build Coastguard Worker )");
418*c8dee2aaSAndroid Build Coastguard Worker 
419*c8dee2aaSAndroid Build Coastguard Worker // This fragment shader is taken from GM_BlurDrawImage.
420*c8dee2aaSAndroid Build Coastguard Worker COMPILER_BENCH(medium, R"(
421*c8dee2aaSAndroid Build Coastguard Worker uniform float3x3 umatrix_S1_c0;
422*c8dee2aaSAndroid Build Coastguard Worker uniform float3x3 umatrix_S2_c0_c0;
423*c8dee2aaSAndroid Build Coastguard Worker uniform float4 urect_S2_c0;
424*c8dee2aaSAndroid Build Coastguard Worker sampler2D uTextureSampler_0_S1;
425*c8dee2aaSAndroid Build Coastguard Worker sampler2D uTextureSampler_0_S2;
426*c8dee2aaSAndroid Build Coastguard Worker flat in half4 vcolor_S0;
427*c8dee2aaSAndroid Build Coastguard Worker noperspective in float2 vTransformedCoords_3_S0;
428*c8dee2aaSAndroid Build Coastguard Worker half4 TextureEffect_S1_c0_c0(half4 _input)
429*c8dee2aaSAndroid Build Coastguard Worker {
430*c8dee2aaSAndroid Build Coastguard Worker 	return sample(uTextureSampler_0_S1, vTransformedCoords_3_S0);
431*c8dee2aaSAndroid Build Coastguard Worker }
432*c8dee2aaSAndroid Build Coastguard Worker half4 MatrixEffect_S1_c0(half4 _input)
433*c8dee2aaSAndroid Build Coastguard Worker {
434*c8dee2aaSAndroid Build Coastguard Worker 	return TextureEffect_S1_c0_c0(_input);
435*c8dee2aaSAndroid Build Coastguard Worker }
436*c8dee2aaSAndroid Build Coastguard Worker half4 DisableCoverageAsAlpha_S1(half4 _input)
437*c8dee2aaSAndroid Build Coastguard Worker {
438*c8dee2aaSAndroid Build Coastguard Worker 	_input = MatrixEffect_S1_c0(_input);
439*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_0_inColor = _input;
440*c8dee2aaSAndroid Build Coastguard Worker 	return half4(_input);
441*c8dee2aaSAndroid Build Coastguard Worker }
442*c8dee2aaSAndroid Build Coastguard Worker half4 TextureEffect_S2_c0_c0_c0(half4 _input, float2 _coords)
443*c8dee2aaSAndroid Build Coastguard Worker {
444*c8dee2aaSAndroid Build Coastguard Worker 	return sample(uTextureSampler_0_S2, _coords).000r;
445*c8dee2aaSAndroid Build Coastguard Worker }
446*c8dee2aaSAndroid Build Coastguard Worker half4 MatrixEffect_S2_c0_c0(half4 _input, float2 _coords)
447*c8dee2aaSAndroid Build Coastguard Worker {
448*c8dee2aaSAndroid Build Coastguard Worker 	return TextureEffect_S2_c0_c0_c0(_input, float3x2(umatrix_S2_c0_c0) * _coords.xy1);
449*c8dee2aaSAndroid Build Coastguard Worker }
450*c8dee2aaSAndroid Build Coastguard Worker half4 RectBlur_S2_c0(half4 _input, float2 _coords)
451*c8dee2aaSAndroid Build Coastguard Worker {
452*c8dee2aaSAndroid Build Coastguard Worker 	half4 _tmp_1_inColor = _input;
453*c8dee2aaSAndroid Build Coastguard Worker 	float2 _tmp_2_coords = _coords;
454*c8dee2aaSAndroid Build Coastguard Worker 	half xCoverage;
455*c8dee2aaSAndroid Build Coastguard Worker 	half yCoverage;
456*c8dee2aaSAndroid Build Coastguard Worker 	if (bool(int(1)))
457*c8dee2aaSAndroid Build Coastguard Worker 	{
458*c8dee2aaSAndroid Build Coastguard Worker 		half2 xy = max(half2(urect_S2_c0.xy - _tmp_2_coords), half2(_tmp_2_coords - urect_S2_c0.zw));
459*c8dee2aaSAndroid Build Coastguard Worker 		xCoverage = MatrixEffect_S2_c0_c0(_tmp_1_inColor, float2(half2(xy.x, 0.5))).w;
460*c8dee2aaSAndroid Build Coastguard Worker 		yCoverage = MatrixEffect_S2_c0_c0(_tmp_1_inColor, float2(half2(xy.y, 0.5))).w;
461*c8dee2aaSAndroid Build Coastguard Worker 	}
462*c8dee2aaSAndroid Build Coastguard Worker 	else
463*c8dee2aaSAndroid Build Coastguard Worker 	{
464*c8dee2aaSAndroid Build Coastguard Worker 		half4 rect = half4(half2(urect_S2_c0.xy - _tmp_2_coords), half2(_tmp_2_coords - urect_S2_c0.zw));
465*c8dee2aaSAndroid Build Coastguard Worker 		xCoverage = (1.0 - MatrixEffect_S2_c0_c0(_tmp_1_inColor, float2(half2(rect.x, 0.5))).w) - MatrixEffect_S2_c0_c0(_tmp_1_inColor, float2(half2(rect.z, 0.5))).w;
466*c8dee2aaSAndroid Build Coastguard Worker 		yCoverage = (1.0 - MatrixEffect_S2_c0_c0(_tmp_1_inColor, float2(half2(rect.y, 0.5))).w) - MatrixEffect_S2_c0_c0(_tmp_1_inColor, float2(half2(rect.w, 0.5))).w;
467*c8dee2aaSAndroid Build Coastguard Worker 	}
468*c8dee2aaSAndroid Build Coastguard Worker 	return half4((_input * xCoverage) * yCoverage);
469*c8dee2aaSAndroid Build Coastguard Worker }
470*c8dee2aaSAndroid Build Coastguard Worker half4 DeviceSpace_S2(half4 _input)
471*c8dee2aaSAndroid Build Coastguard Worker {
472*c8dee2aaSAndroid Build Coastguard Worker 	return RectBlur_S2_c0(_input, sk_FragCoord.xy);
473*c8dee2aaSAndroid Build Coastguard Worker }
474*c8dee2aaSAndroid Build Coastguard Worker void main()
475*c8dee2aaSAndroid Build Coastguard Worker {
476*c8dee2aaSAndroid Build Coastguard Worker 	// Stage 0, QuadPerEdgeAAGeometryProcessor
477*c8dee2aaSAndroid Build Coastguard Worker 	half4 outputColor_S0;
478*c8dee2aaSAndroid Build Coastguard Worker 	outputColor_S0 = vcolor_S0;
479*c8dee2aaSAndroid Build Coastguard Worker 	const half4 outputCoverage_S0 = half4(1);
480*c8dee2aaSAndroid Build Coastguard Worker 	half4 output_S1;
481*c8dee2aaSAndroid Build Coastguard Worker 	output_S1 = DisableCoverageAsAlpha_S1(outputColor_S0);
482*c8dee2aaSAndroid Build Coastguard Worker 	half4 output_S2;
483*c8dee2aaSAndroid Build Coastguard Worker 	output_S2 = DeviceSpace_S2(outputCoverage_S0);
484*c8dee2aaSAndroid Build Coastguard Worker 	{
485*c8dee2aaSAndroid Build Coastguard Worker 		// Xfer Processor: Porter Duff
486*c8dee2aaSAndroid Build Coastguard Worker 		sk_FragColor = output_S1 * output_S2;
487*c8dee2aaSAndroid Build Coastguard Worker 	}
488*c8dee2aaSAndroid Build Coastguard Worker }
489*c8dee2aaSAndroid Build Coastguard Worker )");
490*c8dee2aaSAndroid Build Coastguard Worker 
491*c8dee2aaSAndroid Build Coastguard Worker // This fragment shader is taken from GM_lcdtext.
492*c8dee2aaSAndroid Build Coastguard Worker COMPILER_BENCH(small, R"(
493*c8dee2aaSAndroid Build Coastguard Worker sampler2D uTextureSampler_0_S0;
494*c8dee2aaSAndroid Build Coastguard Worker noperspective in float2 vTextureCoords_S0;
495*c8dee2aaSAndroid Build Coastguard Worker flat in float vTexIndex_S0;
496*c8dee2aaSAndroid Build Coastguard Worker noperspective in half4 vinColor_S0;
497*c8dee2aaSAndroid Build Coastguard Worker void main()
498*c8dee2aaSAndroid Build Coastguard Worker {
499*c8dee2aaSAndroid Build Coastguard Worker 	// Stage 0, BitmapText
500*c8dee2aaSAndroid Build Coastguard Worker 	half4 outputColor_S0;
501*c8dee2aaSAndroid Build Coastguard Worker 	outputColor_S0 = vinColor_S0;
502*c8dee2aaSAndroid Build Coastguard Worker 	half4 texColor;
503*c8dee2aaSAndroid Build Coastguard Worker 	{
504*c8dee2aaSAndroid Build Coastguard Worker 		texColor = sample(uTextureSampler_0_S0, vTextureCoords_S0).rrrr;
505*c8dee2aaSAndroid Build Coastguard Worker 	}
506*c8dee2aaSAndroid Build Coastguard Worker 	half4 outputCoverage_S0 = texColor;
507*c8dee2aaSAndroid Build Coastguard Worker 	{
508*c8dee2aaSAndroid Build Coastguard Worker 		// Xfer Processor: Porter Duff
509*c8dee2aaSAndroid Build Coastguard Worker 		sk_FragColor = outputColor_S0 * outputCoverage_S0;
510*c8dee2aaSAndroid Build Coastguard Worker 	}
511*c8dee2aaSAndroid Build Coastguard Worker }
512*c8dee2aaSAndroid Build Coastguard Worker )");
513*c8dee2aaSAndroid Build Coastguard Worker 
514*c8dee2aaSAndroid Build Coastguard Worker COMPILER_BENCH(tiny, "void main() { sk_FragColor = half4(1); }");
515*c8dee2aaSAndroid Build Coastguard Worker 
516*c8dee2aaSAndroid Build Coastguard Worker #define GRAPHITE_BENCH(name, text)                                                                \
517*c8dee2aaSAndroid Build Coastguard Worker     static constexpr char name##_SRC[] = text;                                                    \
518*c8dee2aaSAndroid Build Coastguard Worker     DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true, Output::kGrMtl);) \
519*c8dee2aaSAndroid Build Coastguard Worker     DEF_BENCH(return new SkSLCompileBench(#name, name##_SRC, /*optimize=*/true, Output::kGrWGSL);)
520*c8dee2aaSAndroid Build Coastguard Worker 
521*c8dee2aaSAndroid Build Coastguard Worker // This fragment shader is from the third tile on the top row of GM_gradients_2pt_conical_outside.
522*c8dee2aaSAndroid Build Coastguard Worker GRAPHITE_BENCH(graphite_large, R"(
523*c8dee2aaSAndroid Build Coastguard Worker layout(location=0) in flat int shadingSsboIndexVar;
524*c8dee2aaSAndroid Build Coastguard Worker layout(location=1) in float2 localCoordsVar;
525*c8dee2aaSAndroid Build Coastguard Worker layout(location=2) in float4 jacobian;
526*c8dee2aaSAndroid Build Coastguard Worker layout(location=3) in float4 edgeDistances;
527*c8dee2aaSAndroid Build Coastguard Worker layout(location=4) in float4 xRadii;
528*c8dee2aaSAndroid Build Coastguard Worker layout(location=5) in float4 yRadii;
529*c8dee2aaSAndroid Build Coastguard Worker layout(location=6) in float2 strokeParams;
530*c8dee2aaSAndroid Build Coastguard Worker layout(location=7) in float2 perPixelControl;
531*c8dee2aaSAndroid Build Coastguard Worker struct FSUniformData
532*c8dee2aaSAndroid Build Coastguard Worker {
533*c8dee2aaSAndroid Build Coastguard Worker 	// 0 - SolidColor uniforms
534*c8dee2aaSAndroid Build Coastguard Worker 	float4 color_0;
535*c8dee2aaSAndroid Build Coastguard Worker 	// 2 - ConicalGradient8 uniforms
536*c8dee2aaSAndroid Build Coastguard Worker 	float4 colors_2[8];
537*c8dee2aaSAndroid Build Coastguard Worker 	float4 offsets_2[2];
538*c8dee2aaSAndroid Build Coastguard Worker 	float2 point0_2;
539*c8dee2aaSAndroid Build Coastguard Worker 	float2 point1_2;
540*c8dee2aaSAndroid Build Coastguard Worker 	float radius0_2;
541*c8dee2aaSAndroid Build Coastguard Worker 	float radius1_2;
542*c8dee2aaSAndroid Build Coastguard Worker 	int tilemode_2;
543*c8dee2aaSAndroid Build Coastguard Worker 	int colorSpace_2;
544*c8dee2aaSAndroid Build Coastguard Worker 	int doUnPremul_2;
545*c8dee2aaSAndroid Build Coastguard Worker 	// 3 - ColorSpaceTransform uniforms
546*c8dee2aaSAndroid Build Coastguard Worker 	int flags_3;
547*c8dee2aaSAndroid Build Coastguard Worker 	int srcKind_3;
548*c8dee2aaSAndroid Build Coastguard Worker 	half3x3 gamutTransform_3;
549*c8dee2aaSAndroid Build Coastguard Worker 	int dstKind_3;
550*c8dee2aaSAndroid Build Coastguard Worker 	half4x4 csXformCoeffs_3;
551*c8dee2aaSAndroid Build Coastguard Worker 	// 4 - DitherShader uniforms
552*c8dee2aaSAndroid Build Coastguard Worker 	half range_4;
553*c8dee2aaSAndroid Build Coastguard Worker }
554*c8dee2aaSAndroid Build Coastguard Worker ;
555*c8dee2aaSAndroid Build Coastguard Worker layout (binding=2) buffer FSUniforms
556*c8dee2aaSAndroid Build Coastguard Worker {
557*c8dee2aaSAndroid Build Coastguard Worker 	FSUniformData fsUniformData[];
558*c8dee2aaSAndroid Build Coastguard Worker }
559*c8dee2aaSAndroid Build Coastguard Worker ;
560*c8dee2aaSAndroid Build Coastguard Worker // 4 - DitherShader samplers
561*c8dee2aaSAndroid Build Coastguard Worker layout(binding=0) sampler2D sampler_4;
562*c8dee2aaSAndroid Build Coastguard Worker // [1]   1: ColorFilterShader
563*c8dee2aaSAndroid Build Coastguard Worker half4 ColorFilterShader_1(half4 inColor, half4 destColor, float2 coords)
564*c8dee2aaSAndroid Build Coastguard Worker {
565*c8dee2aaSAndroid Build Coastguard Worker 	return sk_color_space_transform(sk_conical_grad_8_shader(coords, fsUniformData[shadingSsboIndexVar].colors_2, fsUniformData[shadingSsboIndexVar].offsets_2, fsUniformData[shadingSsboIndexVar].point0_2, fsUniformData[shadingSsboIndexVar].point1_2, fsUniformData[shadingSsboIndexVar].radius0_2, fsUniformData[shadingSsboIndexVar].radius1_2, fsUniformData[shadingSsboIndexVar].tilemode_2, fsUniformData[shadingSsboIndexVar].colorSpace_2, fsUniformData[shadingSsboIndexVar].doUnPremul_2), fsUniformData[shadingSsboIndexVar].flags_3, fsUniformData[shadingSsboIndexVar].srcKind_3, fsUniformData[shadingSsboIndexVar].gamutTransform_3, fsUniformData[shadingSsboIndexVar].dstKind_3, fsUniformData[shadingSsboIndexVar].csXformCoeffs_3);
566*c8dee2aaSAndroid Build Coastguard Worker }
567*c8dee2aaSAndroid Build Coastguard Worker void main()
568*c8dee2aaSAndroid Build Coastguard Worker {
569*c8dee2aaSAndroid Build Coastguard Worker 	half4 initialColor = half4(0);
570*c8dee2aaSAndroid Build Coastguard Worker 	// [0] SolidColor
571*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor_0 = sk_solid_shader(fsUniformData[shadingSsboIndexVar].color_0);
572*c8dee2aaSAndroid Build Coastguard Worker 	// [1] ColorFilterShader
573*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor_1 = ColorFilterShader_1(outColor_0, half4(1), localCoordsVar);
574*c8dee2aaSAndroid Build Coastguard Worker 	// [4] DitherShader
575*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor_4 = sk_dither_shader(outColor_1, localCoordsVar, fsUniformData[shadingSsboIndexVar].range_4, sampler_4);
576*c8dee2aaSAndroid Build Coastguard Worker 	// [5] SrcOver
577*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor_5 = outColor_4;
578*c8dee2aaSAndroid Build Coastguard Worker 	half4 outputCoverage;
579*c8dee2aaSAndroid Build Coastguard Worker 	outputCoverage = analytic_rrect_coverage_fn(sk_FragCoord, jacobian, edgeDistances, xRadii, yRadii, strokeParams, perPixelControl);
580*c8dee2aaSAndroid Build Coastguard Worker 	sk_FragColor = outColor_5 * outputCoverage;
581*c8dee2aaSAndroid Build Coastguard Worker }
582*c8dee2aaSAndroid Build Coastguard Worker )");
583*c8dee2aaSAndroid Build Coastguard Worker 
584*c8dee2aaSAndroid Build Coastguard Worker // This fragment shader is taken from GM_lcdtext.
585*c8dee2aaSAndroid Build Coastguard Worker GRAPHITE_BENCH(graphite_small, R"(
586*c8dee2aaSAndroid Build Coastguard Worker layout(location=0) in flat int shadingSsboIndexVar;
587*c8dee2aaSAndroid Build Coastguard Worker layout(location=1) in float2 textureCoords;
588*c8dee2aaSAndroid Build Coastguard Worker layout(location=2) in half texIndex;
589*c8dee2aaSAndroid Build Coastguard Worker layout(location=3) in half maskFormat;
590*c8dee2aaSAndroid Build Coastguard Worker layout (binding=1) uniform StepUniforms
591*c8dee2aaSAndroid Build Coastguard Worker {
592*c8dee2aaSAndroid Build Coastguard Worker 	layout(offset=0) float4x4 subRunDeviceMatrix;
593*c8dee2aaSAndroid Build Coastguard Worker 	layout(offset=64) float4x4 deviceToLocal;
594*c8dee2aaSAndroid Build Coastguard Worker 	layout(offset=128) float2 atlasSizeInv;
595*c8dee2aaSAndroid Build Coastguard Worker }
596*c8dee2aaSAndroid Build Coastguard Worker ;
597*c8dee2aaSAndroid Build Coastguard Worker struct FSUniformData
598*c8dee2aaSAndroid Build Coastguard Worker {
599*c8dee2aaSAndroid Build Coastguard Worker 	// 0 - SolidColor uniforms
600*c8dee2aaSAndroid Build Coastguard Worker 	float4 color_0;
601*c8dee2aaSAndroid Build Coastguard Worker }
602*c8dee2aaSAndroid Build Coastguard Worker ;
603*c8dee2aaSAndroid Build Coastguard Worker layout (binding=2) buffer FSUniforms
604*c8dee2aaSAndroid Build Coastguard Worker {
605*c8dee2aaSAndroid Build Coastguard Worker 	FSUniformData fsUniformData[];
606*c8dee2aaSAndroid Build Coastguard Worker }
607*c8dee2aaSAndroid Build Coastguard Worker ;
608*c8dee2aaSAndroid Build Coastguard Worker layout(binding=0) sampler2D text_atlas_0;
609*c8dee2aaSAndroid Build Coastguard Worker layout(binding=1) sampler2D text_atlas_1;
610*c8dee2aaSAndroid Build Coastguard Worker layout(binding=2) sampler2D text_atlas_2;
611*c8dee2aaSAndroid Build Coastguard Worker layout(binding=3) sampler2D text_atlas_3;
612*c8dee2aaSAndroid Build Coastguard Worker void main()
613*c8dee2aaSAndroid Build Coastguard Worker {
614*c8dee2aaSAndroid Build Coastguard Worker 	half4 initialColor = half4(0);
615*c8dee2aaSAndroid Build Coastguard Worker 	// [0] SolidColor
616*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor_0 = sk_solid_shader(fsUniformData[shadingSsboIndexVar].color_0);
617*c8dee2aaSAndroid Build Coastguard Worker 	// [1] SrcOver
618*c8dee2aaSAndroid Build Coastguard Worker 	half4 outColor_1 = outColor_0;
619*c8dee2aaSAndroid Build Coastguard Worker 	half4 outputCoverage;
620*c8dee2aaSAndroid Build Coastguard Worker 	outputCoverage = bitmap_text_coverage_fn(sample_indexed_atlas(textureCoords, int(texIndex), text_atlas_0, text_atlas_1, text_atlas_2, text_atlas_3), int(maskFormat));
621*c8dee2aaSAndroid Build Coastguard Worker 	sk_FragColor = outColor_1 * outputCoverage;
622*c8dee2aaSAndroid Build Coastguard Worker }
623*c8dee2aaSAndroid Build Coastguard Worker )");
624*c8dee2aaSAndroid Build Coastguard Worker 
625*c8dee2aaSAndroid Build Coastguard Worker #if defined(SK_BUILD_FOR_UNIX)
626*c8dee2aaSAndroid Build Coastguard Worker 
627*c8dee2aaSAndroid Build Coastguard Worker #include <malloc.h>
heap_bytes_used()628*c8dee2aaSAndroid Build Coastguard Worker static int64_t heap_bytes_used() {
629*c8dee2aaSAndroid Build Coastguard Worker     return (int64_t)mallinfo().uordblks;
630*c8dee2aaSAndroid Build Coastguard Worker }
631*c8dee2aaSAndroid Build Coastguard Worker 
632*c8dee2aaSAndroid Build Coastguard Worker #elif defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS)
633*c8dee2aaSAndroid Build Coastguard Worker 
634*c8dee2aaSAndroid Build Coastguard Worker #include <malloc/malloc.h>
heap_bytes_used()635*c8dee2aaSAndroid Build Coastguard Worker static int64_t heap_bytes_used() {
636*c8dee2aaSAndroid Build Coastguard Worker     malloc_statistics_t stats;
637*c8dee2aaSAndroid Build Coastguard Worker     malloc_zone_pressure_relief(malloc_default_zone(), 0);
638*c8dee2aaSAndroid Build Coastguard Worker     malloc_zone_statistics(malloc_default_zone(), &stats);
639*c8dee2aaSAndroid Build Coastguard Worker     return (int64_t)stats.size_in_use;
640*c8dee2aaSAndroid Build Coastguard Worker }
641*c8dee2aaSAndroid Build Coastguard Worker 
642*c8dee2aaSAndroid Build Coastguard Worker #else
643*c8dee2aaSAndroid Build Coastguard Worker 
heap_bytes_used()644*c8dee2aaSAndroid Build Coastguard Worker static int64_t heap_bytes_used() {
645*c8dee2aaSAndroid Build Coastguard Worker     return -1;
646*c8dee2aaSAndroid Build Coastguard Worker }
647*c8dee2aaSAndroid Build Coastguard Worker 
648*c8dee2aaSAndroid Build Coastguard Worker #endif
649*c8dee2aaSAndroid Build Coastguard Worker 
bench(NanoJSONResultsWriter * log,const char * name,int bytes)650*c8dee2aaSAndroid Build Coastguard Worker static void bench(NanoJSONResultsWriter* log, const char* name, int bytes) {
651*c8dee2aaSAndroid Build Coastguard Worker     SkDEBUGCODE(SkDebugf("%s: %d bytes\n", name, bytes);)
652*c8dee2aaSAndroid Build Coastguard Worker     log->beginObject(name);          // test
653*c8dee2aaSAndroid Build Coastguard Worker     log->beginObject("meta");        //   config
654*c8dee2aaSAndroid Build Coastguard Worker     log->appendS32("bytes", bytes);  //     sub_result
655*c8dee2aaSAndroid Build Coastguard Worker     log->endObject();                //   config
656*c8dee2aaSAndroid Build Coastguard Worker     log->endObject();                // test
657*c8dee2aaSAndroid Build Coastguard Worker }
658*c8dee2aaSAndroid Build Coastguard Worker 
659*c8dee2aaSAndroid Build Coastguard Worker // These benchmarks aren't timed, they produce memory usage statistics. They run standalone, and
660*c8dee2aaSAndroid Build Coastguard Worker // directly add their results to the nanobench log.
RunSkSLModuleBenchmarks(NanoJSONResultsWriter * log)661*c8dee2aaSAndroid Build Coastguard Worker void RunSkSLModuleBenchmarks(NanoJSONResultsWriter* log) {
662*c8dee2aaSAndroid Build Coastguard Worker     // Heap used by a default compiler (with no modules loaded)
663*c8dee2aaSAndroid Build Coastguard Worker     int64_t before = heap_bytes_used();
664*c8dee2aaSAndroid Build Coastguard Worker     SkSL::Compiler compiler;
665*c8dee2aaSAndroid Build Coastguard Worker     int baselineBytes = heap_bytes_used();
666*c8dee2aaSAndroid Build Coastguard Worker     if (baselineBytes >= 0) {
667*c8dee2aaSAndroid Build Coastguard Worker         baselineBytes = (baselineBytes - before);
668*c8dee2aaSAndroid Build Coastguard Worker         bench(log, "sksl_compiler_baseline", baselineBytes);
669*c8dee2aaSAndroid Build Coastguard Worker     }
670*c8dee2aaSAndroid Build Coastguard Worker 
671*c8dee2aaSAndroid Build Coastguard Worker     // Heap used by a compiler with the two main GPU modules (fragment + vertex) and runtime effects
672*c8dee2aaSAndroid Build Coastguard Worker     // (shader + color filter + blender) loaded. Ganesh will load all of these in regular usage.
673*c8dee2aaSAndroid Build Coastguard Worker     before = heap_bytes_used();
674*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kVertex);
675*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kFragment);
676*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kRuntimeColorFilter);
677*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kRuntimeShader);
678*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kRuntimeBlender);
679*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kPrivateRuntimeColorFilter);
680*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kPrivateRuntimeShader);
681*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kPrivateRuntimeBlender);
682*c8dee2aaSAndroid Build Coastguard Worker     int64_t gpuBytes = heap_bytes_used();
683*c8dee2aaSAndroid Build Coastguard Worker     if (gpuBytes >= 0) {
684*c8dee2aaSAndroid Build Coastguard Worker         gpuBytes = (gpuBytes - before) + baselineBytes;
685*c8dee2aaSAndroid Build Coastguard Worker         bench(log, "sksl_compiler_gpu", gpuBytes);
686*c8dee2aaSAndroid Build Coastguard Worker     }
687*c8dee2aaSAndroid Build Coastguard Worker 
688*c8dee2aaSAndroid Build Coastguard Worker #if defined(SK_GRAPHITE)
689*c8dee2aaSAndroid Build Coastguard Worker     // Heap used by a compiler with the Graphite modules loaded.
690*c8dee2aaSAndroid Build Coastguard Worker     before = heap_bytes_used();
691*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kGraphiteVertex);
692*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kGraphiteFragment);
693*c8dee2aaSAndroid Build Coastguard Worker     int64_t graphiteBytes = heap_bytes_used();
694*c8dee2aaSAndroid Build Coastguard Worker     if (graphiteBytes >= 0) {
695*c8dee2aaSAndroid Build Coastguard Worker         graphiteBytes = (graphiteBytes - before) + gpuBytes;
696*c8dee2aaSAndroid Build Coastguard Worker         bench(log, "sksl_compiler_graphite", graphiteBytes);
697*c8dee2aaSAndroid Build Coastguard Worker     }
698*c8dee2aaSAndroid Build Coastguard Worker 
699*c8dee2aaSAndroid Build Coastguard Worker     // Heap used by a compiler with compute-shader support loaded.
700*c8dee2aaSAndroid Build Coastguard Worker     before = heap_bytes_used();
701*c8dee2aaSAndroid Build Coastguard Worker     compiler.moduleForProgramKind(SkSL::ProgramKind::kCompute);
702*c8dee2aaSAndroid Build Coastguard Worker     int64_t computeBytes = heap_bytes_used();
703*c8dee2aaSAndroid Build Coastguard Worker     if (computeBytes >= 0) {
704*c8dee2aaSAndroid Build Coastguard Worker         computeBytes = (computeBytes - before) + baselineBytes;
705*c8dee2aaSAndroid Build Coastguard Worker         bench(log, "sksl_compiler_compute", computeBytes);
706*c8dee2aaSAndroid Build Coastguard Worker     }
707*c8dee2aaSAndroid Build Coastguard Worker #endif
708*c8dee2aaSAndroid Build Coastguard Worker 
709*c8dee2aaSAndroid Build Coastguard Worker     // Report the minified module sizes.
710*c8dee2aaSAndroid Build Coastguard Worker     int compilerGPUBinarySize = std::size(SKSL_MINIFIED_sksl_shared) +
711*c8dee2aaSAndroid Build Coastguard Worker                                 std::size(SKSL_MINIFIED_sksl_gpu) +
712*c8dee2aaSAndroid Build Coastguard Worker                                 std::size(SKSL_MINIFIED_sksl_vert) +
713*c8dee2aaSAndroid Build Coastguard Worker                                 std::size(SKSL_MINIFIED_sksl_frag) +
714*c8dee2aaSAndroid Build Coastguard Worker                                 std::size(SKSL_MINIFIED_sksl_public) +
715*c8dee2aaSAndroid Build Coastguard Worker                                 std::size(SKSL_MINIFIED_sksl_rt_shader);
716*c8dee2aaSAndroid Build Coastguard Worker     bench(log, "sksl_binary_size_gpu", compilerGPUBinarySize);
717*c8dee2aaSAndroid Build Coastguard Worker 
718*c8dee2aaSAndroid Build Coastguard Worker     int compilerGraphiteBinarySize = std::size(SKSL_MINIFIED_sksl_graphite_frag) +
719*c8dee2aaSAndroid Build Coastguard Worker                                      std::size(SKSL_MINIFIED_sksl_graphite_vert);
720*c8dee2aaSAndroid Build Coastguard Worker     bench(log, "sksl_binary_size_graphite", compilerGraphiteBinarySize);
721*c8dee2aaSAndroid Build Coastguard Worker 
722*c8dee2aaSAndroid Build Coastguard Worker     int compilerGraphiteES2BinarySize = std::size(SKSL_MINIFIED_sksl_graphite_frag_es2) +
723*c8dee2aaSAndroid Build Coastguard Worker                                         std::size(SKSL_MINIFIED_sksl_graphite_vert_es2);
724*c8dee2aaSAndroid Build Coastguard Worker     bench(log, "sksl_binary_size_graphite_es2", compilerGraphiteES2BinarySize);
725*c8dee2aaSAndroid Build Coastguard Worker 
726*c8dee2aaSAndroid Build Coastguard Worker     int compilerComputeBinarySize = std::size(SKSL_MINIFIED_sksl_compute);
727*c8dee2aaSAndroid Build Coastguard Worker     bench(log, "sksl_binary_size_compute", compilerComputeBinarySize);
728*c8dee2aaSAndroid Build Coastguard Worker }
729*c8dee2aaSAndroid Build Coastguard Worker 
730*c8dee2aaSAndroid Build Coastguard Worker class SkSLModuleLoaderBench : public Benchmark {
731*c8dee2aaSAndroid Build Coastguard Worker public:
SkSLModuleLoaderBench(const char * name,std::vector<SkSL::ProgramKind> moduleList)732*c8dee2aaSAndroid Build Coastguard Worker     SkSLModuleLoaderBench(const char* name, std::vector<SkSL::ProgramKind> moduleList)
733*c8dee2aaSAndroid Build Coastguard Worker             : fName(name), fModuleList(std::move(moduleList)) {}
734*c8dee2aaSAndroid Build Coastguard Worker 
onGetName()735*c8dee2aaSAndroid Build Coastguard Worker     const char* onGetName() override {
736*c8dee2aaSAndroid Build Coastguard Worker         return fName;
737*c8dee2aaSAndroid Build Coastguard Worker     }
738*c8dee2aaSAndroid Build Coastguard Worker 
isSuitableFor(Backend backend)739*c8dee2aaSAndroid Build Coastguard Worker     bool isSuitableFor(Backend backend) override {
740*c8dee2aaSAndroid Build Coastguard Worker         return backend == Backend::kNonRendering;
741*c8dee2aaSAndroid Build Coastguard Worker     }
742*c8dee2aaSAndroid Build Coastguard Worker 
shouldLoop() const743*c8dee2aaSAndroid Build Coastguard Worker     bool shouldLoop() const override {
744*c8dee2aaSAndroid Build Coastguard Worker         return false;
745*c8dee2aaSAndroid Build Coastguard Worker     }
746*c8dee2aaSAndroid Build Coastguard Worker 
onPreDraw(SkCanvas *)747*c8dee2aaSAndroid Build Coastguard Worker     void onPreDraw(SkCanvas*) override {
748*c8dee2aaSAndroid Build Coastguard Worker         SkSL::ModuleLoader::Get().unloadModules();
749*c8dee2aaSAndroid Build Coastguard Worker     }
750*c8dee2aaSAndroid Build Coastguard Worker 
onDraw(int loops,SkCanvas *)751*c8dee2aaSAndroid Build Coastguard Worker     void onDraw(int loops, SkCanvas*) override {
752*c8dee2aaSAndroid Build Coastguard Worker         SkASSERT(loops == 1);
753*c8dee2aaSAndroid Build Coastguard Worker         SkSL::Compiler compiler;
754*c8dee2aaSAndroid Build Coastguard Worker         for (SkSL::ProgramKind kind : fModuleList) {
755*c8dee2aaSAndroid Build Coastguard Worker             compiler.moduleForProgramKind(kind);
756*c8dee2aaSAndroid Build Coastguard Worker         }
757*c8dee2aaSAndroid Build Coastguard Worker     }
758*c8dee2aaSAndroid Build Coastguard Worker 
759*c8dee2aaSAndroid Build Coastguard Worker     const char* fName;
760*c8dee2aaSAndroid Build Coastguard Worker     std::vector<SkSL::ProgramKind> fModuleList;
761*c8dee2aaSAndroid Build Coastguard Worker };
762*c8dee2aaSAndroid Build Coastguard Worker 
763*c8dee2aaSAndroid Build Coastguard Worker DEF_BENCH(return new SkSLModuleLoaderBench("sksl_module_loader_ganesh",
764*c8dee2aaSAndroid Build Coastguard Worker                                            {
765*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kVertex,
766*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kFragment,
767*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kRuntimeColorFilter,
768*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kRuntimeShader,
769*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kRuntimeBlender,
770*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kPrivateRuntimeColorFilter,
771*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kPrivateRuntimeShader,
772*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kPrivateRuntimeBlender,
773*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kCompute,
774*c8dee2aaSAndroid Build Coastguard Worker                                            });)
775*c8dee2aaSAndroid Build Coastguard Worker 
776*c8dee2aaSAndroid Build Coastguard Worker DEF_BENCH(return new SkSLModuleLoaderBench("sksl_module_loader_graphite",
777*c8dee2aaSAndroid Build Coastguard Worker                                            {
778*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kVertex,
779*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kFragment,
780*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kRuntimeColorFilter,
781*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kRuntimeShader,
782*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kRuntimeBlender,
783*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kPrivateRuntimeColorFilter,
784*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kPrivateRuntimeShader,
785*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kPrivateRuntimeBlender,
786*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kCompute,
787*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kGraphiteVertex,
788*c8dee2aaSAndroid Build Coastguard Worker                                                    SkSL::ProgramKind::kGraphiteFragment,
789*c8dee2aaSAndroid Build Coastguard Worker                                            });)
790