blob: 5336b5b7b9e627300150e99bbb986199e89b8034 [file] [log] [blame]
bsalomon506c8022015-09-14 13:16:26 -07001/*
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
Mike Kleinc0bd9f92019-04-23 12:05:21 -05008#include "src/gpu/GrProcessorUnitTest.h"
bsalomon506c8022015-09-14 13:16:26 -07009
Robert Phillips4e105e22020-07-16 09:18:50 -040010#include "include/gpu/GrRecordingContext.h"
Brian Salomon766098d2019-12-18 10:41:58 -050011#include "src/gpu/GrFragmentProcessor.h"
Robert Phillips4e105e22020-07-16 09:18:50 -040012#include "src/gpu/GrRecordingContextPriv.h"
Brian Salomon766098d2019-12-18 10:41:58 -050013
Hal Canary6f6961e2017-01-31 13:50:44 -050014#if GR_TEST_UTILS
15
John Stileseac4ad72020-07-17 15:46:20 -040016class GrGeometryProcessor;
17
John Stiles6609cb62020-07-17 14:52:12 -040018GrProcessorTestData::GrProcessorTestData(SkRandom* random, GrRecordingContext* context,
John Stiles278b4a62020-07-17 16:44:49 -040019 int numViews, const ViewInfo views[])
20 : GrProcessorTestData(random, context, numViews, views, /*inputFP=*/nullptr) {}
21
22GrProcessorTestData::GrProcessorTestData(SkRandom* random, GrRecordingContext* context,
John Stiles6609cb62020-07-17 14:52:12 -040023 int numViews, const ViewInfo views[],
24 std::unique_ptr<GrFragmentProcessor> inputFP)
25 : fRandom(random), fContext(context), fInputFP(std::move(inputFP)) {
Greg Daniel026a60c2020-02-12 10:53:51 -050026 fViews.reset(views, numViews);
Brian Salomon766098d2019-12-18 10:41:58 -050027 fArena = std::unique_ptr<SkArenaAlloc>(new SkArenaAlloc(1000));
28}
29
John Stilese911ce52020-07-17 13:32:27 -040030GrProcessorTestData::~GrProcessorTestData() {}
Brian Salomon766098d2019-12-18 10:41:58 -050031
32GrProxyProvider* GrProcessorTestData::proxyProvider() { return fContext->priv().proxyProvider(); }
33
34const GrCaps* GrProcessorTestData::caps() { return fContext->priv().caps(); }
35
John Stiles6609cb62020-07-17 14:52:12 -040036std::unique_ptr<GrFragmentProcessor> GrProcessorTestData::inputFP() { return std::move(fInputFP); }
37
Greg Daniel026a60c2020-02-12 10:53:51 -050038GrProcessorTestData::ViewInfo GrProcessorTestData::randomView() {
39 SkASSERT(!fViews.empty());
40 return fViews[fRandom->nextULessThan(fViews.count())];
Brian Salomon766098d2019-12-18 10:41:58 -050041}
42
Greg Daniel026a60c2020-02-12 10:53:51 -050043GrProcessorTestData::ViewInfo GrProcessorTestData::randomAlphaOnlyView() {
Brian Salomon766098d2019-12-18 10:41:58 -050044 int numAlphaOnly = 0;
Greg Daniel026a60c2020-02-12 10:53:51 -050045 for (const auto& [v, ct, at] : fViews) {
Brian Salomon766098d2019-12-18 10:41:58 -050046 if (GrColorTypeIsAlphaOnly(ct)) {
47 ++numAlphaOnly;
48 }
49 }
50 SkASSERT(numAlphaOnly);
51 int idx = fRandom->nextULessThan(numAlphaOnly);
Greg Daniel026a60c2020-02-12 10:53:51 -050052 for (const auto& [v, ct, at] : fViews) {
Brian Salomon766098d2019-12-18 10:41:58 -050053 if (GrColorTypeIsAlphaOnly(ct) && !idx--) {
Greg Daniel026a60c2020-02-12 10:53:51 -050054 return {v, ct, at};
Brian Salomon766098d2019-12-18 10:41:58 -050055 }
56 }
57 SkUNREACHABLE;
58}
59
John Stileseac4ad72020-07-17 15:46:20 -040060template <class ProcessorSmartPtr>
61GrProcessorTestFactory<ProcessorSmartPtr>::GrProcessorTestFactory(MakeProc makeProc) {
62 fMakeProc = makeProc;
63 GetFactories()->push_back(this);
64}
65
66template <class ProcessorSmartPtr>
67ProcessorSmartPtr GrProcessorTestFactory<ProcessorSmartPtr>::Make(GrProcessorTestData* data) {
68 VerifyFactoryCount();
69 if (GetFactories()->count() == 0) {
70 return nullptr;
71 }
72 uint32_t idx = data->fRandom->nextULessThan(GetFactories()->count());
73 return MakeIdx(idx, data);
74}
75
76template <class ProcessorSmartPtr>
77ProcessorSmartPtr GrProcessorTestFactory<ProcessorSmartPtr>::MakeIdx(int idx,
78 GrProcessorTestData* data) {
79 SkASSERT(idx < GetFactories()->count());
80 GrProcessorTestFactory<ProcessorSmartPtr>* factory = (*GetFactories())[idx];
81 ProcessorSmartPtr processor = factory->fMakeProc(data);
82 SkASSERT(processor);
83 return processor;
84}
85
86template <class ProcessorSmartPtr>
87int GrProcessorTestFactory<ProcessorSmartPtr>::Count() {
88 return GetFactories()->count();
89}
90
91GrXPFactoryTestFactory::GrXPFactoryTestFactory(GetFn* getProc) : fGetProc(getProc) {
92 GetFactories()->push_back(this);
93}
94
95const GrXPFactory* GrXPFactoryTestFactory::Get(GrProcessorTestData* data) {
96 VerifyFactoryCount();
97 if (GetFactories()->count() == 0) {
98 return nullptr;
99 }
100 uint32_t idx = data->fRandom->nextRangeU(0, GetFactories()->count() - 1);
101 const GrXPFactory* xpf = (*GetFactories())[idx]->fGetProc(data);
102 SkASSERT(xpf);
103 return xpf;
104}
Brian Salomon766098d2019-12-18 10:41:58 -0500105
106/*
107 * Originally these were both in the processor unit test header, but then it seemed to cause linker
108 * problems on android.
109 */
110template <>
111SkTArray<GrFragmentProcessorTestFactory*, true>* GrFragmentProcessorTestFactory::GetFactories() {
112 static SkTArray<GrFragmentProcessorTestFactory*, true> gFactories;
113 return &gFactories;
114}
115
116template <>
117SkTArray<GrGeometryProcessorTestFactory*, true>* GrGeometryProcessorTestFactory::GetFactories() {
118 static SkTArray<GrGeometryProcessorTestFactory*, true> gFactories;
119 return &gFactories;
120}
121
122SkTArray<GrXPFactoryTestFactory*, true>* GrXPFactoryTestFactory::GetFactories() {
123 static SkTArray<GrXPFactoryTestFactory*, true> gFactories;
124 return &gFactories;
125}
126
127/*
128 * To ensure we always have successful static initialization, before creating from the factories
129 * we verify the count is as expected. If a new factory is added, then these numbers must be
130 * manually adjusted.
131 */
John Stileseac4ad72020-07-17 15:46:20 -0400132static constexpr int kFPFactoryCount = 37;
133static constexpr int kGPFactoryCount = 14;
134static constexpr int kXPFactoryCount = 4;
Brian Salomon766098d2019-12-18 10:41:58 -0500135
136template <> void GrFragmentProcessorTestFactory::VerifyFactoryCount() {
137 if (kFPFactoryCount != GetFactories()->count()) {
138 SkDebugf("\nExpected %d fragment processor factories, found %d.\n", kFPFactoryCount,
139 GetFactories()->count());
140 SK_ABORT("Wrong number of fragment processor factories!");
141 }
142}
143
144template <> void GrGeometryProcessorTestFactory::VerifyFactoryCount() {
145 if (kGPFactoryCount != GetFactories()->count()) {
146 SkDebugf("\nExpected %d geometry processor factories, found %d.\n", kGPFactoryCount,
147 GetFactories()->count());
148 SK_ABORT("Wrong number of geometry processor factories!");
149 }
150}
151
152void GrXPFactoryTestFactory::VerifyFactoryCount() {
153 if (kXPFactoryCount != GetFactories()->count()) {
154 SkDebugf("\nExpected %d xp factory factories, found %d.\n", kXPFactoryCount,
155 GetFactories()->count());
156 SK_ABORT("Wrong number of xp factory factories!");
157 }
158}
159
Brian Salomonaff329b2017-08-11 09:40:37 -0400160std::unique_ptr<GrFragmentProcessor> GrProcessorUnitTest::MakeChildFP(GrProcessorTestData* data) {
Brian Salomonaff329b2017-08-11 09:40:37 -0400161 std::unique_ptr<GrFragmentProcessor> fp;
bsalomon506c8022015-09-14 13:16:26 -0700162 do {
Brian Salomon1c053642017-07-24 10:16:19 -0400163 fp = GrFragmentProcessorTestFactory::Make(data);
bsalomon506c8022015-09-14 13:16:26 -0700164 SkASSERT(fp);
Brian Osman12c5d292020-07-13 16:11:35 -0400165 } while (fp->numNonNullChildProcessors() != 0);
bungeman06ca8ec2016-06-09 08:01:03 -0700166 return fp;
bsalomon506c8022015-09-14 13:16:26 -0700167}
John Stileseac4ad72020-07-17 15:46:20 -0400168
169template class GrProcessorTestFactory<GrGeometryProcessor*>;
170template class GrProcessorTestFactory<std::unique_ptr<GrFragmentProcessor>>;
171
Hal Canary6f6961e2017-01-31 13:50:44 -0500172#endif