OLD | NEW |
---|---|
(Empty) | |
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 | |
8 #include "Fuzz.h" | |
9 #include "SkCanvas.h" | |
10 #include "SkSurface.h" | |
11 #include "SkGradientShader.h" | |
12 | |
13 #include <algorithm> | |
14 | |
15 const int MAX_COUNT = 400; | |
16 | |
17 bool makeMatrix(Fuzz* fuzz, SkMatrix* m) { | |
18 SkScalar scaleX, skewX, transX, skewY, scaleY, transY, persp0, persp1, persp2; | |
f(malita)
2016/08/11 16:06:20
General formatting: 4-space indentation, per Skia
kjlubick
2016/08/11 17:15:25
Done.
| |
19 if (!fuzz->next<SkScalar>(&scaleX) || | |
20 !fuzz->next<SkScalar>(&skewX) || | |
21 !fuzz->next<SkScalar>(&transX) || | |
22 !fuzz->next<SkScalar>(&skewY) || | |
23 !fuzz->next<SkScalar>(&scaleY) || | |
24 !fuzz->next<SkScalar>(&transY) || | |
25 !fuzz->next<SkScalar>(&persp0) || | |
26 !fuzz->next<SkScalar>(&persp1) || | |
27 !fuzz->next<SkScalar>(&persp2)) { | |
28 return false; | |
29 } | |
30 m->setAll(scaleX, skewX, transX, skewY, scaleY, transY, persp0, persp1, persp2 ); | |
31 return true; | |
32 } | |
33 | |
34 bool initColors(Fuzz* fuzz, uint32_t* count, SkColor** colors, SkScalar** pos, | |
f(malita)
2016/08/11 16:06:20
Nit: rename to initGradientParams?
kjlubick
2016/08/11 17:15:25
Done.
| |
35 SkShader::TileMode* mode) { | |
36 if (fuzz->remaining() < sizeof(uint32_t)) { | |
37 return false; | |
38 } | |
39 uint32_t t_count; | |
40 SkColor* t_colors; | |
41 SkScalar* t_pos; | |
42 | |
43 t_count = fuzz->nextRangeU(0, MAX_COUNT); | |
44 if (t_count == 1) { | |
45 t_count = 2; | |
46 } | |
47 | |
48 if (fuzz->remaining() < (1 + t_count * (sizeof(SkColor) + sizeof(SkScalar)))) { | |
49 return false; | |
50 } | |
51 t_colors = new SkColor[t_count]; | |
52 t_pos = new SkScalar[t_count]; | |
53 for (uint32_t i = 0; i < t_count; i++) { | |
54 SkColor col; | |
55 SkScalar s; | |
56 fuzz->next<SkColor>(&col); | |
57 fuzz->next<SkScalar>(&s); | |
58 (t_colors)[i] = col; | |
59 (t_pos)[i] = s; | |
60 } | |
61 | |
62 if (t_count == 0) { | |
63 *count = 0; | |
64 *colors = NULL; | |
65 *pos = NULL; | |
66 } else { | |
67 std::sort(t_pos, t_pos + t_count); | |
68 t_pos[0] = 0; | |
69 t_pos[t_count - 1] = 1; | |
70 *count = t_count; | |
71 *colors = t_colors; | |
72 *pos = t_pos; | |
73 } | |
74 | |
75 *mode = static_cast<SkShader::TileMode>(fuzz->nextRangeU(0, 3)); | |
76 return true; | |
77 } | |
78 | |
79 void fuzzLinearGradient(Fuzz* fuzz) { | |
80 SkScalar a, b, c, d; | |
81 bool useLocalMatrix, useGlobalMatrix; | |
82 if (!fuzz->next<SkScalar>(&a) || | |
83 !fuzz->next<SkScalar>(&b) || | |
84 !fuzz->next<SkScalar>(&c) || | |
85 !fuzz->next<SkScalar>(&d) || | |
86 !fuzz->next<bool>(&useLocalMatrix) || | |
87 !fuzz->next<bool>(&useGlobalMatrix)) { | |
88 return; | |
89 } | |
90 SkPoint pts[2] = {SkPoint::Make(a,b), SkPoint::Make(c, d)}; | |
91 | |
92 uint32_t count; | |
93 SkColor* colors; | |
94 SkScalar* pos; | |
f(malita)
2016/08/11 16:06:20
Do we ever deallocate these?
Maybe refactor using
kjlubick
2016/08/11 17:15:25
See below for explanation that when the return hap
| |
95 SkShader::TileMode mode; | |
96 if (!initColors(fuzz, &count, &colors, &pos, &mode)) { | |
97 return; | |
98 } | |
99 | |
100 SkPaint p; | |
101 if (useLocalMatrix) { | |
102 SkMatrix m; | |
103 if (!makeMatrix(fuzz, &m)) { | |
104 return; | |
105 } | |
106 uint32_t flags; | |
107 if (!fuzz->next(&flags)) { | |
f(malita)
2016/08/11 16:06:20
The (poorly documented?) flags parameter is not re
kjlubick
2016/08/11 17:15:25
Done, using your refactor below.
| |
108 return; | |
109 } | |
110 p.setShader(SkGradientShader::MakeLinear(pts, colors, pos, count, mode, fl ags, &m)); | |
111 } | |
112 else { | |
113 p.setShader(SkGradientShader::MakeLinear(pts, colors, pos, count, mode)); | |
114 } | |
f(malita)
2016/08/11 16:06:20
Nit: Skia-idiomatic refactor idea for this block,
kjlubick
2016/08/11 17:15:25
Done.
| |
115 | |
116 sk_sp<SkSurface> surface(SkSurface::MakeRasterN32Premul(50, 50)); | |
f(malita)
2016/08/11 16:06:20
I think this would run much faster if we hoisted t
kjlubick
2016/08/11 17:15:25
This fuzzer code isn't like the "fuzz unit tests"
| |
117 if (useGlobalMatrix) { | |
118 SkMatrix gm; | |
119 if (!makeMatrix(fuzz, &gm)) { | |
120 return; | |
121 } | |
122 SkCanvas* c = surface->getCanvas(); | |
123 c->setMatrix(gm); | |
124 c->drawPaint(p); | |
125 } else { | |
126 surface->getCanvas()->drawPaint(p); | |
127 } | |
128 } | |
129 | |
130 void fuzzRadialGradient(Fuzz* fuzz) { | |
131 SkScalar a, b, radius; | |
132 bool useLocalMatrix, useGlobalMatrix; | |
133 if (!fuzz->next<SkScalar>(&a) || | |
134 !fuzz->next<SkScalar>(&b) || | |
135 !fuzz->next<SkScalar>(&radius) || | |
136 !fuzz->next<bool>(&useLocalMatrix) || | |
137 !fuzz->next<bool>(&useGlobalMatrix)) { | |
138 return; | |
139 } | |
140 SkPoint center = SkPoint::Make(a,b); | |
141 | |
142 uint32_t count; | |
143 SkColor* colors; | |
144 SkScalar* pos; | |
145 SkShader::TileMode mode; | |
146 if (!initColors(fuzz, &count, &colors, &pos, &mode)) { | |
147 return; | |
148 } | |
149 | |
150 SkPaint p; | |
151 if (useLocalMatrix) { | |
152 SkMatrix m; | |
153 if (!makeMatrix(fuzz, &m)) { | |
154 return; | |
155 } | |
156 uint32_t flags; | |
157 if (!fuzz->next(&flags)) { | |
158 return; | |
159 } | |
160 p.setShader(SkGradientShader::MakeRadial(center, radius, colors, pos, coun t, mode, flags, &m)); | |
161 } else { | |
162 p.setShader(SkGradientShader::MakeRadial(center, radius, colors, pos, coun t, mode)); | |
163 } | |
164 | |
165 sk_sp<SkSurface> surface(SkSurface::MakeRasterN32Premul(50, 50)); | |
166 if (useGlobalMatrix) { | |
167 SkMatrix gm; | |
168 if (!makeMatrix(fuzz, &gm)) { | |
169 return; | |
170 } | |
171 SkCanvas* c = surface->getCanvas(); | |
172 c->setMatrix(gm); | |
173 c->drawPaint(p); | |
174 } else { | |
175 surface->getCanvas()->drawPaint(p); | |
176 } | |
177 } | |
178 | |
179 void fuzzTwoPointConicalGradient(Fuzz* fuzz) { | |
180 SkScalar a, b, startRadius, c, d, endRadius; | |
181 bool useLocalMatrix, useGlobalMatrix; | |
182 if (!fuzz->next<SkScalar>(&a) || | |
183 !fuzz->next<SkScalar>(&b) || | |
184 !fuzz->next<SkScalar>(&startRadius) || | |
185 !fuzz->next<SkScalar>(&c) || | |
186 !fuzz->next<SkScalar>(&d) || | |
187 !fuzz->next<SkScalar>(&endRadius) || | |
188 !fuzz->next<bool>(&useLocalMatrix) || | |
189 !fuzz->next<bool>(&useGlobalMatrix)) { | |
190 return; | |
191 } | |
192 SkPoint start = SkPoint::Make(a, b); | |
193 SkPoint end = SkPoint::Make(c, d); | |
194 | |
195 uint32_t count; | |
196 SkColor* colors; | |
197 SkScalar* pos; | |
198 SkShader::TileMode mode; | |
199 if (!initColors(fuzz, &count, &colors, &pos, &mode)) { | |
200 return; | |
201 } | |
202 | |
203 SkPaint p; | |
204 if (useLocalMatrix) { | |
205 SkMatrix m; | |
206 if (!makeMatrix(fuzz, &m)) { | |
207 return; | |
208 } | |
209 uint32_t flags; | |
210 if (!fuzz->next(&flags)) { | |
211 return; | |
212 } | |
213 p.setShader(SkGradientShader::MakeTwoPointConical(start, startRadius, end, endRadius, colors, pos, count, mode, flags, &m)); | |
214 } else { | |
215 p.setShader(SkGradientShader::MakeTwoPointConical(start, startRadius, end, endRadius, colors, pos, count, mode)); | |
216 } | |
217 | |
218 sk_sp<SkSurface> surface(SkSurface::MakeRasterN32Premul(50, 50)); | |
219 if (useGlobalMatrix) { | |
220 SkMatrix gm; | |
221 if (!makeMatrix(fuzz, &gm)) { | |
222 return; | |
223 } | |
224 SkCanvas* c = surface->getCanvas(); | |
225 c->setMatrix(gm); | |
226 c->drawPaint(p); | |
227 } else { | |
228 surface->getCanvas()->drawPaint(p); | |
229 } | |
230 } | |
231 | |
232 void fuzzSweepGradient(Fuzz* fuzz) { | |
233 SkScalar cx, cy; | |
234 bool useLocalMatrix, useGlobalMatrix; | |
235 if (!fuzz->next<SkScalar>(&cx) || | |
236 !fuzz->next<SkScalar>(&cy) || | |
237 !fuzz->next<bool>(&useLocalMatrix) || | |
238 !fuzz->next<bool>(&useGlobalMatrix)) { | |
239 return; | |
240 } | |
241 | |
242 uint32_t count; | |
243 SkColor* colors; | |
244 SkScalar* pos; | |
245 SkShader::TileMode mode; | |
246 if (!initColors(fuzz, &count, &colors, &pos, &mode)) { | |
247 return; | |
248 } | |
249 | |
250 SkPaint p; | |
251 if (useLocalMatrix) { | |
252 SkMatrix m; | |
253 if (!makeMatrix(fuzz, &m)) { | |
254 return; | |
255 } | |
256 uint32_t flags; | |
257 if (!fuzz->next(&flags)) { | |
258 return; | |
259 } | |
260 p.setShader(SkGradientShader::MakeSweep(cx, cy, colors, pos, count, flags, &m)); | |
261 } else { | |
262 p.setShader(SkGradientShader::MakeSweep(cx, cy, colors, pos, count)); | |
263 } | |
264 | |
265 | |
266 sk_sp<SkSurface> surface(SkSurface::MakeRasterN32Premul(50, 50)); | |
267 if (useGlobalMatrix) { | |
268 SkMatrix gm; | |
269 if (!makeMatrix(fuzz, &gm)) { | |
270 return; | |
271 } | |
272 SkCanvas* c = surface->getCanvas(); | |
273 c->setMatrix(gm); | |
274 c->drawPaint(p); | |
275 } else { | |
276 surface->getCanvas()->drawPaint(p); | |
277 } | |
278 } | |
279 | |
280 DEF_FUZZ(Gradients, fuzz) { | |
281 uint8_t i; | |
282 if (!fuzz->next<uint8_t>(&i)) { | |
283 return; | |
284 } | |
285 | |
286 switch(i) { | |
287 case 0: | |
288 SkDebugf("LinearGradient\n"); | |
289 fuzzLinearGradient(fuzz); | |
290 return; | |
291 case 1: | |
292 SkDebugf("RadialGradient\n"); | |
293 fuzzRadialGradient(fuzz); | |
294 return; | |
295 case 2: | |
296 SkDebugf("TwoPointConicalGradient\n"); | |
297 fuzzTwoPointConicalGradient(fuzz); | |
298 return; | |
299 } | |
300 SkDebugf("SweepGradient\n"); | |
301 fuzzSweepGradient(fuzz); | |
302 return; | |
303 } | |
OLD | NEW |