• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2014 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 "PathOpsTSectDebug.h"
9 #include "SkOpCoincidence.h"
10 #include "SkOpContour.h"
11 #include "SkIntersectionHelper.h"
12 #include "SkMutex.h"
13 #include "SkOpSegment.h"
14 #include "SkString.h"
15 
DebugDumpDouble(double x)16 inline void DebugDumpDouble(double x) {
17     if (x == floor(x)) {
18         SkDebugf("%.0f", x);
19     } else {
20         SkDebugf("%1.19g", x);
21     }
22 }
23 
DebugDumpFloat(float x)24 inline void DebugDumpFloat(float x) {
25     if (x == floorf(x)) {
26         SkDebugf("%.0f", x);
27     } else {
28         SkDebugf("%1.9gf", x);
29     }
30 }
31 
DebugDumpHexFloat(float x)32 inline void DebugDumpHexFloat(float x) {
33     SkDebugf("SkBits2Float(0x%08x)", SkFloat2Bits(x));
34 }
35 
36 // if not defined by PathOpsDebug.cpp ...
37 #if !defined SK_DEBUG && FORCE_RELEASE
ValidWind(int wind)38 bool SkPathOpsDebug::ValidWind(int wind) {
39     return wind > SK_MinS32 + 0xFFFF && wind < SK_MaxS32 - 0xFFFF;
40 }
41 
WindingPrintf(int wind)42 void SkPathOpsDebug::WindingPrintf(int wind) {
43     if (wind == SK_MinS32) {
44         SkDebugf("?");
45     } else {
46         SkDebugf("%d", wind);
47     }
48 }
49 #endif
50 
DumpID(int id)51 static void DumpID(int id) {
52     SkDebugf("} ");
53     if (id >= 0) {
54         SkDebugf("id=%d", id);
55     }
56     SkDebugf("\n");
57 }
58 
dump() const59 void SkDConic::dump() const {
60     dumpInner();
61     SkDebugf("},\n");
62 }
63 
dumpID(int id) const64 void SkDConic::dumpID(int id) const {
65     dumpInner();
66     DumpID(id);
67 }
68 
dumpInner() const69 void SkDConic::dumpInner() const {
70     SkDebugf("{");
71     fPts.dumpInner();
72     SkDebugf("}}, %1.9gf", fWeight);
73 }
74 
dump() const75 void SkDCubic::dump() const {
76     this->dumpInner();
77     SkDebugf("}},\n");
78 }
79 
dumpID(int id) const80 void SkDCubic::dumpID(int id) const {
81     this->dumpInner();
82     SkDebugf("}");
83     DumpID(id);
84 }
85 
double_is_NaN(double x)86 static inline bool double_is_NaN(double x) { return x != x; }
87 
dumpInner() const88 void SkDCubic::dumpInner() const {
89     SkDebugf("{{");
90     int index = 0;
91     do {
92         if (index != 0) {
93             if (double_is_NaN(fPts[index].fX) && double_is_NaN(fPts[index].fY)) {
94                 return;
95             }
96             SkDebugf(", ");
97         }
98         fPts[index].dump();
99     } while (++index < 3);
100     if (double_is_NaN(fPts[index].fX) && double_is_NaN(fPts[index].fY)) {
101         return;
102     }
103     SkDebugf(", ");
104     fPts[index].dump();
105 }
106 
dump() const107 void SkDCurve::dump() const {
108     dumpID(-1);
109 }
110 
dumpID(int id) const111 void SkDCurve::dumpID(int id) const {
112 #ifndef SK_RELEASE
113     switch(fVerb) {
114         case SkPath::kLine_Verb:
115             fLine.dumpID(id);
116             break;
117         case SkPath::kQuad_Verb:
118             fQuad.dumpID(id);
119             break;
120         case SkPath::kConic_Verb:
121             fConic.dumpID(id);
122             break;
123         case SkPath::kCubic_Verb:
124             fCubic.dumpID(id);
125             break;
126         default:
127             SkASSERT(0);
128     }
129 #else
130     fCubic.dumpID(id);
131 #endif
132 }
133 
dump() const134 void SkDLine::dump() const {
135     this->dumpInner();
136     SkDebugf("}},\n");
137 }
138 
dumpID(int id) const139 void SkDLine::dumpID(int id) const {
140     this->dumpInner();
141     SkDebugf("}");
142     DumpID(id);
143 }
144 
dumpInner() const145 void SkDLine::dumpInner() const {
146     SkDebugf("{{");
147     fPts[0].dump();
148     SkDebugf(", ");
149     fPts[1].dump();
150 }
151 
dump() const152 void SkDPoint::dump() const {
153     SkDebugf("{");
154     DebugDumpDouble(fX);
155     SkDebugf(", ");
156     DebugDumpDouble(fY);
157     SkDebugf("}");
158 }
159 
Dump(const SkPoint & pt)160 void SkDPoint::Dump(const SkPoint& pt) {
161     SkDebugf("{");
162     DebugDumpFloat(pt.fX);
163     SkDebugf(", ");
164     DebugDumpFloat(pt.fY);
165     SkDebugf("}");
166 }
167 
DumpHex(const SkPoint & pt)168 void SkDPoint::DumpHex(const SkPoint& pt) {
169     SkDebugf("{");
170     DebugDumpHexFloat(pt.fX);
171     SkDebugf(", ");
172     DebugDumpHexFloat(pt.fY);
173     SkDebugf("}");
174 }
175 
dump() const176 void SkDQuad::dump() const {
177     dumpInner();
178     SkDebugf("}},\n");
179 }
180 
dumpID(int id) const181 void SkDQuad::dumpID(int id) const {
182     dumpInner();
183     SkDebugf("}");
184     DumpID(id);
185 }
186 
dumpInner() const187 void SkDQuad::dumpInner() const {
188     SkDebugf("{{");
189     int index = 0;
190     do {
191         fPts[index].dump();
192         SkDebugf(", ");
193     } while (++index < 2);
194     fPts[index].dump();
195 }
196 
dump() const197 void SkIntersections::dump() const {
198     SkDebugf("used=%d of %d", fUsed, fMax);
199     for (int index = 0; index < fUsed; ++index) {
200         SkDebugf(" t=(%s%1.9g,%s%1.9g) pt=(%1.9g,%1.9g)",
201                 fIsCoincident[0] & (1 << index) ? "*" : "", fT[0][index],
202                 fIsCoincident[1] & (1 << index) ? "*" : "", fT[1][index],
203                 fPt[index].fX, fPt[index].fY);
204         if (index < 2 && fNearlySame[index]) {
205             SkDebugf(" pt2=(%1.9g,%1.9g)",fPt2[index].fX, fPt2[index].fY);
206         }
207     }
208     SkDebugf("\n");
209 }
210 
DebugAngleAngle(const SkOpAngle * angle,int id)211 const SkOpAngle* SkPathOpsDebug::DebugAngleAngle(const SkOpAngle* angle, int id) {
212     return angle->debugAngle(id);
213 }
214 
DebugAngleContour(SkOpAngle * angle,int id)215 SkOpContour* SkPathOpsDebug::DebugAngleContour(SkOpAngle* angle, int id) {
216     return angle->debugContour(id);
217 }
218 
DebugAnglePtT(const SkOpAngle * angle,int id)219 const SkOpPtT* SkPathOpsDebug::DebugAnglePtT(const SkOpAngle* angle, int id) {
220     return angle->debugPtT(id);
221 }
222 
DebugAngleSegment(const SkOpAngle * angle,int id)223 const SkOpSegment* SkPathOpsDebug::DebugAngleSegment(const SkOpAngle* angle, int id) {
224     return angle->debugSegment(id);
225 }
226 
DebugAngleSpan(const SkOpAngle * angle,int id)227 const SkOpSpanBase* SkPathOpsDebug::DebugAngleSpan(const SkOpAngle* angle, int id) {
228     return angle->debugSpan(id);
229 }
230 
DebugContourAngle(SkOpContour * contour,int id)231 const SkOpAngle* SkPathOpsDebug::DebugContourAngle(SkOpContour* contour, int id) {
232     return contour->debugAngle(id);
233 }
234 
DebugContourContour(SkOpContour * contour,int id)235 SkOpContour* SkPathOpsDebug::DebugContourContour(SkOpContour* contour, int id) {
236     return contour->debugContour(id);
237 }
238 
DebugContourPtT(SkOpContour * contour,int id)239 const SkOpPtT* SkPathOpsDebug::DebugContourPtT(SkOpContour* contour, int id) {
240     return contour->debugPtT(id);
241 }
242 
DebugContourSegment(SkOpContour * contour,int id)243 const SkOpSegment* SkPathOpsDebug::DebugContourSegment(SkOpContour* contour, int id) {
244     return contour->debugSegment(id);
245 }
246 
DebugContourSpan(SkOpContour * contour,int id)247 const SkOpSpanBase* SkPathOpsDebug::DebugContourSpan(SkOpContour* contour, int id) {
248     return contour->debugSpan(id);
249 }
250 
DebugCoincidenceAngle(SkOpCoincidence * coin,int id)251 const SkOpAngle* SkPathOpsDebug::DebugCoincidenceAngle(SkOpCoincidence* coin, int id) {
252     return coin->debugAngle(id);
253 }
254 
DebugCoincidenceContour(SkOpCoincidence * coin,int id)255 SkOpContour* SkPathOpsDebug::DebugCoincidenceContour(SkOpCoincidence* coin, int id) {
256     return coin->debugContour(id);
257 }
258 
DebugCoincidencePtT(SkOpCoincidence * coin,int id)259 const SkOpPtT* SkPathOpsDebug::DebugCoincidencePtT(SkOpCoincidence* coin, int id) {
260     return coin->debugPtT(id);
261 }
262 
DebugCoincidenceSegment(SkOpCoincidence * coin,int id)263 const SkOpSegment* SkPathOpsDebug::DebugCoincidenceSegment(SkOpCoincidence* coin, int id) {
264     return coin->debugSegment(id);
265 }
266 
DebugCoincidenceSpan(SkOpCoincidence * coin,int id)267 const SkOpSpanBase* SkPathOpsDebug::DebugCoincidenceSpan(SkOpCoincidence* coin, int id) {
268     return coin->debugSpan(id);
269 }
270 
DebugPtTAngle(const SkOpPtT * ptT,int id)271 const SkOpAngle* SkPathOpsDebug::DebugPtTAngle(const SkOpPtT* ptT, int id) {
272     return ptT->debugAngle(id);
273 }
274 
DebugPtTContour(SkOpPtT * ptT,int id)275 SkOpContour* SkPathOpsDebug::DebugPtTContour(SkOpPtT* ptT, int id) {
276     return ptT->debugContour(id);
277 }
278 
DebugPtTPtT(const SkOpPtT * ptT,int id)279 const SkOpPtT* SkPathOpsDebug::DebugPtTPtT(const SkOpPtT* ptT, int id) {
280     return ptT->debugPtT(id);
281 }
282 
DebugPtTSegment(const SkOpPtT * ptT,int id)283 const SkOpSegment* SkPathOpsDebug::DebugPtTSegment(const SkOpPtT* ptT, int id) {
284     return ptT->debugSegment(id);
285 }
286 
DebugPtTSpan(const SkOpPtT * ptT,int id)287 const SkOpSpanBase* SkPathOpsDebug::DebugPtTSpan(const SkOpPtT* ptT, int id) {
288     return ptT->debugSpan(id);
289 }
290 
DebugSegmentAngle(const SkOpSegment * span,int id)291 const SkOpAngle* SkPathOpsDebug::DebugSegmentAngle(const SkOpSegment* span, int id) {
292     return span->debugAngle(id);
293 }
294 
DebugSegmentContour(SkOpSegment * span,int id)295 SkOpContour* SkPathOpsDebug::DebugSegmentContour(SkOpSegment* span, int id) {
296     return span->debugContour(id);
297 }
298 
DebugSegmentPtT(const SkOpSegment * span,int id)299 const SkOpPtT* SkPathOpsDebug::DebugSegmentPtT(const SkOpSegment* span, int id) {
300     return span->debugPtT(id);
301 }
302 
DebugSegmentSegment(const SkOpSegment * span,int id)303 const SkOpSegment* SkPathOpsDebug::DebugSegmentSegment(const SkOpSegment* span, int id) {
304     return span->debugSegment(id);
305 }
306 
DebugSegmentSpan(const SkOpSegment * span,int id)307 const SkOpSpanBase* SkPathOpsDebug::DebugSegmentSpan(const SkOpSegment* span, int id) {
308     return span->debugSpan(id);
309 }
310 
DebugSpanAngle(const SkOpSpanBase * span,int id)311 const SkOpAngle* SkPathOpsDebug::DebugSpanAngle(const SkOpSpanBase* span, int id) {
312     return span->debugAngle(id);
313 }
314 
DebugSpanContour(SkOpSpanBase * span,int id)315 SkOpContour* SkPathOpsDebug::DebugSpanContour(SkOpSpanBase* span, int id) {
316     return span->debugContour(id);
317 }
318 
DebugSpanPtT(const SkOpSpanBase * span,int id)319 const SkOpPtT* SkPathOpsDebug::DebugSpanPtT(const SkOpSpanBase* span, int id) {
320     return span->debugPtT(id);
321 }
322 
DebugSpanSegment(const SkOpSpanBase * span,int id)323 const SkOpSegment* SkPathOpsDebug::DebugSpanSegment(const SkOpSpanBase* span, int id) {
324     return span->debugSegment(id);
325 }
326 
DebugSpanSpan(const SkOpSpanBase * span,int id)327 const SkOpSpanBase* SkPathOpsDebug::DebugSpanSpan(const SkOpSpanBase* span, int id) {
328     return span->debugSpan(id);
329 }
330 
331 #if DEBUG_COIN
DumpCoinDict()332 void SkPathOpsDebug::DumpCoinDict() {
333     gCoinSumChangedDict.dump("unused coin algorithm", false);
334     gCoinSumVisitedDict.dump("visited coin function", true);
335 }
336 
dump(const char * str,bool visitCheck) const337 void SkPathOpsDebug::CoinDict::dump(const char* str, bool visitCheck) const {
338     int count = fDict.count();
339     for (int index = 0; index < count; ++index) {
340         const auto& entry = fDict[index];
341         if (visitCheck || entry.fGlitchType == kUninitialized_Glitch) {
342             SkDebugf("%s %s : line %d iteration %d", str, entry.fFunctionName,
343                     entry.fLineNumber, entry.fIteration);
344             DumpGlitchType(entry.fGlitchType);
345             SkDebugf("\n");
346         }
347     }
348 }
349 #endif
350 
dumpContours() const351 void SkOpContour::dumpContours() const {
352     SkOpContour* contour = this->globalState()->contourHead();
353     do {
354         contour->dump();
355     } while ((contour = contour->next()));
356 }
357 
dumpContoursAll() const358 void SkOpContour::dumpContoursAll() const {
359     SkOpContour* contour = this->globalState()->contourHead();
360     do {
361         contour->dumpAll();
362     } while ((contour = contour->next()));
363 }
364 
dumpContoursAngles() const365 void SkOpContour::dumpContoursAngles() const {
366     SkOpContour* contour = this->globalState()->contourHead();
367     do {
368         contour->dumpAngles();
369     } while ((contour = contour->next()));
370 }
371 
dumpContoursPts() const372 void SkOpContour::dumpContoursPts() const {
373     SkOpContour* contour = this->globalState()->contourHead();
374     do {
375         contour->dumpPts();
376     } while ((contour = contour->next()));
377 }
378 
dumpContoursPt(int segmentID) const379 void SkOpContour::dumpContoursPt(int segmentID) const {
380     SkOpContour* contour = this->globalState()->contourHead();
381     do {
382         contour->dumpPt(segmentID);
383     } while ((contour = contour->next()));
384 }
385 
dumpContoursSegment(int segmentID) const386 void SkOpContour::dumpContoursSegment(int segmentID) const {
387     SkOpContour* contour = this->globalState()->contourHead();
388     do {
389         contour->dumpSegment(segmentID);
390     } while ((contour = contour->next()));
391 }
392 
dumpContoursSpan(int spanID) const393 void SkOpContour::dumpContoursSpan(int spanID) const {
394     SkOpContour* contour = this->globalState()->contourHead();
395     do {
396         contour->dumpSpan(spanID);
397     } while ((contour = contour->next()));
398 }
399 
dumpContoursSpans() const400 void SkOpContour::dumpContoursSpans() const {
401     SkOpContour* contour = this->globalState()->contourHead();
402     do {
403         contour->dumpSpans();
404     } while ((contour = contour->next()));
405 }
406 
407 template <typename TCurve, typename OppCurve>
DebugSpan(const SkTSect<TCurve,OppCurve> * sect,int id)408 const SkTSpan<TCurve, OppCurve>* DebugSpan(const SkTSect<TCurve, OppCurve>* sect, int id) {
409     return sect->debugSpan(id);
410 }
411 
412 void DontCallDebugSpan(int id);
DontCallDebugSpan(int id)413 void DontCallDebugSpan(int id) {  // exists to instantiate the templates
414     SkDQuad quad;
415     SkDConic conic;
416     SkDCubic cubic;
417     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
418     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
419     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
420     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
421     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
422     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
423     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
424     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
425     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
426     DebugSpan(&q1q2, id);
427     DebugSpan(&q1k2, id);
428     DebugSpan(&q1c2, id);
429     DebugSpan(&k1q2, id);
430     DebugSpan(&k1k2, id);
431     DebugSpan(&k1c2, id);
432     DebugSpan(&c1q2, id);
433     DebugSpan(&c1k2, id);
434     DebugSpan(&c1c2, id);
435 }
436 
437 template <typename TCurve, typename OppCurve>
DebugT(const SkTSect<TCurve,OppCurve> * sect,double t)438 const SkTSpan<TCurve, OppCurve>* DebugT(const SkTSect<TCurve, OppCurve>* sect, double t) {
439     return sect->debugT(t);
440 }
441 
442 void DontCallDebugT(double t);
DontCallDebugT(double t)443 void DontCallDebugT(double t) {  // exists to instantiate the templates
444     SkDQuad quad;
445     SkDConic conic;
446     SkDCubic cubic;
447     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
448     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
449     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
450     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
451     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
452     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
453     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
454     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
455     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
456     DebugT(&q1q2, t);
457     DebugT(&q1k2, t);
458     DebugT(&q1c2, t);
459     DebugT(&k1q2, t);
460     DebugT(&k1k2, t);
461     DebugT(&k1c2, t);
462     DebugT(&c1q2, t);
463     DebugT(&c1k2, t);
464     DebugT(&c1c2, t);
465 }
466 
467 template <typename TCurve, typename OppCurve>
Dump(const SkTSect<TCurve,OppCurve> * sect)468 void Dump(const SkTSect<TCurve, OppCurve>* sect) {
469     sect->dump();
470 }
471 
472 void DontCallDumpTSect();
DontCallDumpTSect()473 void DontCallDumpTSect() {  // exists to instantiate the templates
474     SkDQuad quad;
475     SkDConic conic;
476     SkDCubic cubic;
477     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
478     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
479     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
480     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
481     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
482     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
483     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
484     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
485     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
486     Dump(&q1q2);
487     Dump(&q1k2);
488     Dump(&q1c2);
489     Dump(&k1q2);
490     Dump(&k1k2);
491     Dump(&k1c2);
492     Dump(&c1q2);
493     Dump(&c1k2);
494     Dump(&c1c2);
495 }
496 
497 template <typename TCurve, typename OppCurve>
DumpBoth(SkTSect<TCurve,OppCurve> * sect1,SkTSect<OppCurve,TCurve> * sect2)498 void DumpBoth(SkTSect<TCurve, OppCurve>* sect1, SkTSect<OppCurve, TCurve>* sect2) {
499     sect1->dumpBoth(sect2);
500 }
501 
502 void DontCallDumpBoth();
DontCallDumpBoth()503 void DontCallDumpBoth() {  // exists to instantiate the templates
504     SkDQuad quad;
505     SkDConic conic;
506     SkDCubic cubic;
507     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
508     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
509     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
510     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
511     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
512     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
513     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
514     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
515     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
516     DumpBoth(&q1q2, &q1q2);
517     DumpBoth(&q1k2, &k1q2);
518     DumpBoth(&q1c2, &c1q2);
519     DumpBoth(&k1q2, &q1k2);
520     DumpBoth(&k1k2, &k1k2);
521     DumpBoth(&k1c2, &c1k2);
522     DumpBoth(&c1q2, &q1c2);
523     DumpBoth(&c1k2, &k1c2);
524     DumpBoth(&c1c2, &c1c2);
525 }
526 
527 template <typename TCurve, typename OppCurve>
DumpBounded(SkTSect<TCurve,OppCurve> * sect1,int id)528 void DumpBounded(SkTSect<TCurve, OppCurve>* sect1, int id) {
529     sect1->dumpBounded(id);
530 }
531 
532 void DontCallDumpBounded();
DontCallDumpBounded()533 void DontCallDumpBounded() {
534     SkDQuad quad;
535     SkDConic conic;
536     SkDCubic cubic;
537     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
538     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
539     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
540     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
541     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
542     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
543     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
544     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
545     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
546     DumpBounded(&q1q2, 0);
547     DumpBounded(&q1k2, 0);
548     DumpBounded(&q1c2, 0);
549     DumpBounded(&k1q2, 0);
550     DumpBounded(&k1k2, 0);
551     DumpBounded(&k1c2, 0);
552     DumpBounded(&c1q2, 0);
553     DumpBounded(&c1k2, 0);
554     DumpBounded(&c1c2, 0);
555 }
556 
557 template <typename TCurve, typename OppCurve>
DumpBounds(SkTSect<TCurve,OppCurve> * sect1)558 void DumpBounds(SkTSect<TCurve, OppCurve>* sect1) {
559     sect1->dumpBounds();
560 }
561 
562 void DontCallDumpBounds();
DontCallDumpBounds()563 void DontCallDumpBounds() {
564     SkDQuad quad;
565     SkDConic conic;
566     SkDCubic cubic;
567     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
568     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
569     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
570     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
571     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
572     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
573     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
574     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
575     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
576     DumpBounds(&q1q2);
577     DumpBounds(&q1k2);
578     DumpBounds(&q1c2);
579     DumpBounds(&k1q2);
580     DumpBounds(&k1k2);
581     DumpBounds(&k1c2);
582     DumpBounds(&c1q2);
583     DumpBounds(&c1k2);
584     DumpBounds(&c1c2);
585 }
586 
587 template <typename TCurve, typename OppCurve>
DumpCoin(SkTSect<TCurve,OppCurve> * sect1)588 void DumpCoin(SkTSect<TCurve, OppCurve>* sect1) {
589     sect1->dumpCoin();
590 }
591 
592 void DontCallDumpCoin();
DontCallDumpCoin()593 void DontCallDumpCoin() {  // exists to instantiate the templates
594     SkDQuad quad;
595     SkDConic conic;
596     SkDCubic cubic;
597     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
598     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
599     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
600     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
601     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
602     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
603     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
604     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
605     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
606     DumpCoin(&q1q2);
607     DumpCoin(&q1k2);
608     DumpCoin(&q1c2);
609     DumpCoin(&k1q2);
610     DumpCoin(&k1k2);
611     DumpCoin(&k1c2);
612     DumpCoin(&c1q2);
613     DumpCoin(&c1k2);
614     DumpCoin(&c1c2);
615 }
616 
617 template <typename TCurve, typename OppCurve>
DumpCoinCurves(SkTSect<TCurve,OppCurve> * sect1)618 void DumpCoinCurves(SkTSect<TCurve, OppCurve>* sect1) {
619     sect1->dumpCoinCurves();
620 }
621 
622 void DontCallDumpCoinCurves();
DontCallDumpCoinCurves()623 void DontCallDumpCoinCurves() {  // exists to instantiate the templates
624     SkDQuad quad;
625     SkDConic conic;
626     SkDCubic cubic;
627     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
628     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
629     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
630     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
631     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
632     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
633     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
634     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
635     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
636     DumpCoinCurves(&q1q2);
637     DumpCoinCurves(&q1k2);
638     DumpCoinCurves(&q1c2);
639     DumpCoinCurves(&k1q2);
640     DumpCoinCurves(&k1k2);
641     DumpCoinCurves(&k1c2);
642     DumpCoinCurves(&c1q2);
643     DumpCoinCurves(&c1k2);
644     DumpCoinCurves(&c1c2);
645 }
646 
647 template <typename TCurve, typename OppCurve>
DumpCurves(const SkTSect<TCurve,OppCurve> * sect)648 void DumpCurves(const SkTSect<TCurve, OppCurve>* sect) {
649     sect->dumpCurves();
650 }
651 
652 void DontCallDumpCurves();
DontCallDumpCurves()653 void DontCallDumpCurves() {  // exists to instantiate the templates
654     SkDQuad quad;
655     SkDConic conic;
656     SkDCubic cubic;
657     SkTSect<SkDQuad, SkDQuad> q1q2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
658     SkTSect<SkDQuad, SkDConic> q1k2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
659     SkTSect<SkDQuad, SkDCubic> q1c2(quad  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
660     SkTSect<SkDConic, SkDQuad> k1q2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
661     SkTSect<SkDConic, SkDConic> k1k2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
662     SkTSect<SkDConic, SkDCubic> k1c2(conic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
663     SkTSect<SkDCubic, SkDQuad> c1q2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
664     SkTSect<SkDCubic, SkDConic> c1k2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
665     SkTSect<SkDCubic, SkDCubic> c1c2(cubic  SkDEBUGPARAMS(nullptr)  PATH_OPS_DEBUG_T_SECT_PARAMS(1));
666     DumpCurves(&q1q2);
667     DumpCurves(&q1k2);
668     DumpCurves(&q1c2);
669     DumpCurves(&k1q2);
670     DumpCurves(&k1k2);
671     DumpCurves(&k1c2);
672     DumpCurves(&c1q2);
673     DumpCurves(&c1k2);
674     DumpCurves(&c1c2);
675 }
676 
677 template <typename TCurve, typename OppCurve>
Dump(const SkTSpan<TCurve,OppCurve> * span)678 void Dump(const SkTSpan<TCurve, OppCurve>* span) {
679     span->dump();
680 }
681 
682 void DontCallDumpTSpan();
DontCallDumpTSpan()683 void DontCallDumpTSpan() {  // exists to instantiate the templates
684     SkTSpan<SkDQuad, SkDQuad> q1q2; q1q2.debugInit();
685     SkTSpan<SkDQuad, SkDConic> q1k2; q1k2.debugInit();
686     SkTSpan<SkDQuad, SkDCubic> q1c2; q1c2.debugInit();
687     SkTSpan<SkDConic, SkDQuad> k1q2; k1q2.debugInit();
688     SkTSpan<SkDConic, SkDConic> k1k2; k1k2.debugInit();
689     SkTSpan<SkDConic, SkDCubic> k1c2; k1c2.debugInit();
690     SkTSpan<SkDCubic, SkDQuad> c1q2; c1q2.debugInit();
691     SkTSpan<SkDCubic, SkDConic> c1k2; c1k2.debugInit();
692     SkTSpan<SkDCubic, SkDCubic> c1c2; c1c2.debugInit();
693     Dump(&q1q2);
694     Dump(&q1k2);
695     Dump(&q1c2);
696     Dump(&k1q2);
697     Dump(&k1k2);
698     Dump(&k1c2);
699     Dump(&c1q2);
700     Dump(&c1k2);
701     Dump(&c1c2);
702 }
703 
704 template <typename TCurve, typename OppCurve>
DumpAll(const SkTSpan<TCurve,OppCurve> * span)705 void DumpAll(const SkTSpan<TCurve, OppCurve>* span) {
706     span->dumpAll();
707 }
708 
709 void DontCallDumpSpanAll();
DontCallDumpSpanAll()710 void DontCallDumpSpanAll() {  // exists to instantiate the templates
711     SkTSpan<SkDQuad, SkDQuad> q1q2; q1q2.debugInit();
712     SkTSpan<SkDQuad, SkDConic> q1k2; q1k2.debugInit();
713     SkTSpan<SkDQuad, SkDCubic> q1c2; q1c2.debugInit();
714     SkTSpan<SkDConic, SkDQuad> k1q2; k1q2.debugInit();
715     SkTSpan<SkDConic, SkDConic> k1k2; k1k2.debugInit();
716     SkTSpan<SkDConic, SkDCubic> k1c2; k1c2.debugInit();
717     SkTSpan<SkDCubic, SkDQuad> c1q2; c1q2.debugInit();
718     SkTSpan<SkDCubic, SkDConic> c1k2; c1k2.debugInit();
719     SkTSpan<SkDCubic, SkDCubic> c1c2; c1c2.debugInit();
720     DumpAll(&q1q2);
721     DumpAll(&q1k2);
722     DumpAll(&q1c2);
723     DumpAll(&k1q2);
724     DumpAll(&k1k2);
725     DumpAll(&k1c2);
726     DumpAll(&c1q2);
727     DumpAll(&c1k2);
728     DumpAll(&c1c2);
729 }
730 
731 template <typename TCurve, typename OppCurve>
DumpBounded(const SkTSpan<TCurve,OppCurve> * span)732 void DumpBounded(const SkTSpan<TCurve, OppCurve>* span) {
733     span->dumpBounded(0);
734 }
735 
736 void DontCallDumpSpanBounded();
DontCallDumpSpanBounded()737 void DontCallDumpSpanBounded() {  // exists to instantiate the templates
738     SkTSpan<SkDQuad, SkDQuad> q1q2; q1q2.debugInit();
739     SkTSpan<SkDQuad, SkDConic> q1k2; q1k2.debugInit();
740     SkTSpan<SkDQuad, SkDCubic> q1c2; q1c2.debugInit();
741     SkTSpan<SkDConic, SkDQuad> k1q2; k1q2.debugInit();
742     SkTSpan<SkDConic, SkDConic> k1k2; k1k2.debugInit();
743     SkTSpan<SkDConic, SkDCubic> k1c2; k1c2.debugInit();
744     SkTSpan<SkDCubic, SkDQuad> c1q2; c1q2.debugInit();
745     SkTSpan<SkDCubic, SkDConic> c1k2; c1k2.debugInit();
746     SkTSpan<SkDCubic, SkDCubic> c1c2; c1c2.debugInit();
747     DumpBounded(&q1q2);
748     DumpBounded(&q1k2);
749     DumpBounded(&q1c2);
750     DumpBounded(&k1q2);
751     DumpBounded(&k1k2);
752     DumpBounded(&k1c2);
753     DumpBounded(&c1q2);
754     DumpBounded(&c1k2);
755     DumpBounded(&c1c2);
756 }
757 
758 template <typename TCurve, typename OppCurve>
DumpCoin(const SkTSpan<TCurve,OppCurve> * span)759 void DumpCoin(const SkTSpan<TCurve, OppCurve>* span) {
760     span->dumpCoin();
761 }
762 
763 void DontCallDumpSpanCoin();
DontCallDumpSpanCoin()764 void DontCallDumpSpanCoin() {  // exists to instantiate the templates
765     SkTSpan<SkDQuad, SkDQuad> q1q2; q1q2.debugInit();
766     SkTSpan<SkDQuad, SkDConic> q1k2; q1k2.debugInit();
767     SkTSpan<SkDQuad, SkDCubic> q1c2; q1c2.debugInit();
768     SkTSpan<SkDConic, SkDQuad> k1q2; k1q2.debugInit();
769     SkTSpan<SkDConic, SkDConic> k1k2; k1k2.debugInit();
770     SkTSpan<SkDConic, SkDCubic> k1c2; k1c2.debugInit();
771     SkTSpan<SkDCubic, SkDQuad> c1q2; c1q2.debugInit();
772     SkTSpan<SkDCubic, SkDConic> c1k2; c1k2.debugInit();
773     SkTSpan<SkDCubic, SkDCubic> c1c2; c1c2.debugInit();
774     DumpCoin(&q1q2);
775     DumpCoin(&q1k2);
776     DumpCoin(&q1c2);
777     DumpCoin(&k1q2);
778     DumpCoin(&k1k2);
779     DumpCoin(&k1c2);
780     DumpCoin(&c1q2);
781     DumpCoin(&c1k2);
782     DumpCoin(&c1c2);
783 }
784 
dumpTestCase(const SkDQuad & quad1,const SkDQuad & quad2,int testNo)785 static void dumpTestCase(const SkDQuad& quad1, const SkDQuad& quad2, int testNo) {
786     SkDebugf("\n<div id=\"quad%d\">\n", testNo);
787     quad1.dumpInner();
788     SkDebugf("}}, ");
789     quad2.dump();
790     SkDebugf("</div>\n\n");
791 }
792 
dumpTestTrailer()793 static void dumpTestTrailer() {
794     SkDebugf("</div>\n\n<script type=\"text/javascript\">\n\n");
795     SkDebugf("    var testDivs = [\n");
796 }
797 
dumpTestList(int testNo,double min)798 static void dumpTestList(int testNo, double min) {
799     SkDebugf("        quad%d,", testNo);
800     if (min > 0) {
801         SkDebugf("  // %1.9g", min);
802     }
803     SkDebugf("\n");
804 }
805 
DumpQ(const SkDQuad & quad1,const SkDQuad & quad2,int testNo)806 void DumpQ(const SkDQuad& quad1, const SkDQuad& quad2, int testNo) {
807     SkDebugf("\n");
808     dumpTestCase(quad1, quad2, testNo);
809     dumpTestTrailer();
810     dumpTestList(testNo, 0);
811     SkDebugf("\n");
812 }
813 
DumpT(const SkDQuad & quad,double t)814 void DumpT(const SkDQuad& quad, double t) {
815     SkDLine line = {{quad.ptAtT(t), quad[0]}};
816     line.dump();
817 }
818 
debugAngle(int id) const819 const SkOpAngle* SkOpAngle::debugAngle(int id) const {
820     return this->segment()->debugAngle(id);
821 }
822 
debugCoincidence() const823 const SkOpCoincidence* SkOpAngle::debugCoincidence() const {
824     return this->segment()->debugCoincidence();
825 }
826 
debugContour(int id) const827 SkOpContour* SkOpAngle::debugContour(int id) const {
828     return this->segment()->debugContour(id);
829 }
830 
debugPtT(int id) const831 const SkOpPtT* SkOpAngle::debugPtT(int id) const {
832     return this->segment()->debugPtT(id);
833 }
834 
debugSegment(int id) const835 const SkOpSegment* SkOpAngle::debugSegment(int id) const {
836     return this->segment()->debugSegment(id);
837 }
838 
debugSign() const839 int SkOpAngle::debugSign() const {
840     SkASSERT(fStart->t() != fEnd->t());
841     return fStart->t() < fEnd->t() ? -1 : 1;
842 }
843 
debugSpan(int id) const844 const SkOpSpanBase* SkOpAngle::debugSpan(int id) const {
845     return this->segment()->debugSpan(id);
846 }
847 
dump() const848 void SkOpAngle::dump() const {
849     dumpOne(true);
850     SkDebugf("\n");
851 }
852 
dumpOne(bool functionHeader) const853 void SkOpAngle::dumpOne(bool functionHeader) const {
854 //    fSegment->debugValidate();
855     const SkOpSegment* segment = this->segment();
856     const SkOpSpan& mSpan = *fStart->starter(fEnd);
857     if (functionHeader) {
858         SkDebugf("%s ", __FUNCTION__);
859     }
860     SkDebugf("[%d", segment->debugID());
861     SkDebugf("/%d", debugID());
862     SkDebugf("] next=");
863     if (fNext) {
864         SkDebugf("%d", fNext->fStart->segment()->debugID());
865         SkDebugf("/%d", fNext->debugID());
866     } else {
867         SkDebugf("?");
868     }
869     SkDebugf(" sect=%d/%d ", fSectorStart, fSectorEnd);
870     SkDebugf(" s=%1.9g [%d] e=%1.9g [%d]", fStart->t(), fStart->debugID(),
871                 fEnd->t(), fEnd->debugID());
872     SkDebugf(" sgn=%d windVal=%d", this->debugSign(), mSpan.windValue());
873 
874     SkDebugf(" windSum=");
875     SkPathOpsDebug::WindingPrintf(mSpan.windSum());
876     if (mSpan.oppValue() != 0 || mSpan.oppSum() != SK_MinS32) {
877         SkDebugf(" oppVal=%d", mSpan.oppValue());
878         SkDebugf(" oppSum=");
879         SkPathOpsDebug::WindingPrintf(mSpan.oppSum());
880     }
881     if (mSpan.done()) {
882         SkDebugf(" done");
883     }
884     if (unorderable()) {
885         SkDebugf(" unorderable");
886     }
887     if (segment->operand()) {
888         SkDebugf(" operand");
889     }
890 }
891 
dumpTo(const SkOpSegment * segment,const SkOpAngle * to) const892 void SkOpAngle::dumpTo(const SkOpSegment* segment, const SkOpAngle* to) const {
893     const SkOpAngle* first = this;
894     const SkOpAngle* next = this;
895     const char* indent = "";
896     do {
897         SkDebugf("%s", indent);
898         next->dumpOne(false);
899         if (segment == next->fStart->segment()) {
900             if (this == fNext) {
901                 SkDebugf(" << from");
902             }
903             if (to == fNext) {
904                 SkDebugf(" << to");
905             }
906         }
907         SkDebugf("\n");
908         indent = "           ";
909         next = next->fNext;
910     } while (next && next != first);
911 }
912 
dumpCurves() const913 void SkOpAngle::dumpCurves() const {
914     const SkOpAngle* first = this;
915     const SkOpAngle* next = this;
916     do {
917         next->fPart.fCurve.dumpID(next->segment()->debugID());
918         next = next->fNext;
919     } while (next && next != first);
920 }
921 
dumpLoop() const922 void SkOpAngle::dumpLoop() const {
923     const SkOpAngle* first = this;
924     const SkOpAngle* next = this;
925     do {
926         next->dumpOne(false);
927         SkDebugf("\n");
928         next = next->fNext;
929     } while (next && next != first);
930 }
931 
dumpTest() const932 void SkOpAngle::dumpTest() const {
933     const SkOpAngle* first = this;
934     const SkOpAngle* next = this;
935     do {
936         SkDebugf("{ ");
937         SkOpSegment* segment = next->segment();
938         segment->dumpPts();
939         SkDebugf(", %d, %1.9g, %1.9g, {} },\n", SkPathOpsVerbToPoints(segment->verb()) + 1,
940                 next->start()->t(), next->end()->t());
941         next = next->fNext;
942     } while (next && next != first);
943 }
944 
debugMatchID(int id) const945 bool SkOpPtT::debugMatchID(int id) const {
946     int limit = this->debugLoopLimit(false);
947     int loop = 0;
948     const SkOpPtT* ptT = this;
949     do {
950         if (ptT->debugID() == id) {
951             return true;
952         }
953     } while ((!limit || ++loop <= limit) && (ptT = ptT->next()) && ptT != this);
954     return false;
955 }
956 
debugAngle(int id) const957 const SkOpAngle* SkOpPtT::debugAngle(int id) const {
958     return this->span()->debugAngle(id);
959 }
960 
debugContour(int id) const961 SkOpContour* SkOpPtT::debugContour(int id) const {
962     return this->span()->debugContour(id);
963 }
964 
debugCoincidence() const965 const SkOpCoincidence* SkOpPtT::debugCoincidence() const {
966     return this->span()->debugCoincidence();
967 }
968 
debugPtT(int id) const969 const SkOpPtT* SkOpPtT::debugPtT(int id) const {
970     return this->span()->debugPtT(id);
971 }
972 
debugSegment(int id) const973 const SkOpSegment* SkOpPtT::debugSegment(int id) const {
974     return this->span()->debugSegment(id);
975 }
976 
debugSpan(int id) const977 const SkOpSpanBase* SkOpPtT::debugSpan(int id) const {
978     return this->span()->debugSpan(id);
979 }
980 
dump() const981 void SkOpPtT::dump() const {
982     SkDebugf("seg=%d span=%d ptT=%d",
983             this->segment()->debugID(), this->span()->debugID(), this->debugID());
984     this->dumpBase();
985     SkDebugf("\n");
986 }
987 
dumpAll() const988 void SkOpPtT::dumpAll() const {
989     contour()->indentDump();
990     const SkOpPtT* next = this;
991     int limit = debugLoopLimit(true);
992     int loop = 0;
993     do {
994         SkDebugf("%.*s", contour()->debugIndent(), "        ");
995         SkDebugf("seg=%d span=%d ptT=%d",
996                 next->segment()->debugID(), next->span()->debugID(), next->debugID());
997         next->dumpBase();
998         SkDebugf("\n");
999         if (limit && ++loop >= limit) {
1000             SkDebugf("*** abort loop ***\n");
1001             break;
1002         }
1003     } while ((next = next->fNext) && next != this);
1004     contour()->outdentDump();
1005 }
1006 
dumpBase() const1007 void SkOpPtT::dumpBase() const {
1008     SkDebugf(" t=%1.9g pt=(%1.9g,%1.9g)%s%s%s", this->fT, this->fPt.fX, this->fPt.fY,
1009             this->fCoincident ? " coin" : "",
1010             this->fDuplicatePt ? " dup" : "", this->fDeleted ? " deleted" : "");
1011 }
1012 
debugAngle(int id) const1013 const SkOpAngle* SkOpSpanBase::debugAngle(int id) const {
1014     return this->segment()->debugAngle(id);
1015 }
1016 
debugCoincidence() const1017 const SkOpCoincidence* SkOpSpanBase::debugCoincidence() const {
1018     return this->segment()->debugCoincidence();
1019 }
1020 
debugContour(int id) const1021 SkOpContour* SkOpSpanBase::debugContour(int id) const {
1022     return this->segment()->debugContour(id);
1023 }
1024 
debugPtT(int id) const1025 const SkOpPtT* SkOpSpanBase::debugPtT(int id) const {
1026     return this->segment()->debugPtT(id);
1027 }
1028 
debugSegment(int id) const1029 const SkOpSegment* SkOpSpanBase::debugSegment(int id) const {
1030     return this->segment()->debugSegment(id);
1031 }
1032 
debugSpan(int id) const1033 const SkOpSpanBase* SkOpSpanBase::debugSpan(int id) const {
1034     return this->segment()->debugSpan(id);
1035 }
1036 
dump() const1037 void SkOpSpanBase::dump() const {
1038     this->dumpHead();
1039     this->fPtT.dump();
1040 }
1041 
dumpHead() const1042 void SkOpSpanBase::dumpHead() const {
1043     SkDebugf("%.*s", contour()->debugIndent(), "        ");
1044     SkDebugf("seg=%d span=%d", this->segment()->debugID(), this->debugID());
1045     this->dumpBase();
1046     SkDebugf("\n");
1047 }
1048 
dumpAll() const1049 void SkOpSpanBase::dumpAll() const {
1050     this->dumpHead();
1051     this->fPtT.dumpAll();
1052 }
1053 
dumpBase() const1054 void SkOpSpanBase::dumpBase() const {
1055     if (this->fAligned) {
1056         SkDebugf(" aligned");
1057     }
1058     if (this->fChased) {
1059         SkDebugf(" chased");
1060     }
1061 #ifdef SK_DEBUG
1062     if (this->fDebugDeleted) {
1063         SkDebugf(" deleted");
1064     }
1065 #endif
1066     if (!this->final()) {
1067         this->upCast()->dumpSpan();
1068     }
1069     const SkOpSpanBase* coin = this->coinEnd();
1070     if (this != coin) {
1071         SkDebugf(" coinEnd seg/span=%d/%d", coin->segment()->debugID(), coin->debugID());
1072     } else if (this->final() || !this->upCast()->isCoincident()) {
1073         const SkOpPtT* oPt = this->ptT()->next();
1074         SkDebugf(" seg/span=%d/%d", oPt->segment()->debugID(), oPt->span()->debugID());
1075     }
1076     SkDebugf(" adds=%d", fSpanAdds);
1077 }
1078 
dumpCoin() const1079 void SkOpSpanBase::dumpCoin() const {
1080     const SkOpSpan* span = this->upCastable();
1081     if (!span) {
1082         return;
1083     }
1084     if (!span->isCoincident()) {
1085         return;
1086     }
1087     span->dumpCoin();
1088 }
1089 
dumpCoin() const1090 void SkOpSpan::dumpCoin() const {
1091     const SkOpSpan* coincident = fCoincident;
1092     bool ok = debugCoinLoopCheck();
1093     this->dump();
1094     int loop = 0;
1095     do {
1096         coincident->dump();
1097         if (!ok && ++loop > 10) {
1098             SkDebugf("*** abort loop ***\n");
1099             break;
1100         }
1101     } while ((coincident = coincident->fCoincident) != this);
1102 }
1103 
dumpSpan() const1104 bool SkOpSpan::dumpSpan() const {
1105     SkOpSpan* coin = fCoincident;
1106     if (this != coin) {
1107         SkDebugf(" coinStart seg/span=%d/%d", coin->segment()->debugID(), coin->debugID());
1108     }
1109     SkDebugf(" windVal=%d", this->windValue());
1110     SkDebugf(" windSum=");
1111     SkPathOpsDebug::WindingPrintf(this->windSum());
1112     if (this->oppValue() != 0 || this->oppSum() != SK_MinS32) {
1113         SkDebugf(" oppVal=%d", this->oppValue());
1114         SkDebugf(" oppSum=");
1115         SkPathOpsDebug::WindingPrintf(this->oppSum());
1116     }
1117     if (this->done()) {
1118         SkDebugf(" done");
1119     }
1120     return this != coin;
1121 }
1122 
debugAngle(int id) const1123 const SkOpAngle* SkOpSegment::debugAngle(int id) const {
1124     return this->contour()->debugAngle(id);
1125 }
1126 
1127 
debugCoincidence() const1128 const SkOpCoincidence* SkOpSegment::debugCoincidence() const {
1129     return this->contour()->debugCoincidence();
1130 }
1131 
debugContour(int id) const1132 SkOpContour* SkOpSegment::debugContour(int id) const {
1133     return this->contour()->debugContour(id);
1134 }
1135 
debugPtT(int id) const1136 const SkOpPtT* SkOpSegment::debugPtT(int id) const {
1137     return this->contour()->debugPtT(id);
1138 }
1139 
debugSegment(int id) const1140 const SkOpSegment* SkOpSegment::debugSegment(int id) const {
1141     return this->contour()->debugSegment(id);
1142 }
1143 
debugSpan(int id) const1144 const SkOpSpanBase* SkOpSegment::debugSpan(int id) const {
1145     return this->contour()->debugSpan(id);
1146 }
1147 
dump() const1148 void SkOpSegment::dump() const {
1149     SkDebugf("%.*s", contour()->debugIndent(), "        ");
1150     this->dumpPts();
1151     const SkOpSpanBase* span = &fHead;
1152     contour()->indentDump();
1153     do {
1154         SkDebugf("%.*s span=%d ", contour()->debugIndent(), "        ", span->debugID());
1155         span->ptT()->dumpBase();
1156         span->dumpBase();
1157         SkDebugf("\n");
1158     } while (!span->final() && (span = span->upCast()->next()));
1159     contour()->outdentDump();
1160 }
1161 
dumpAll() const1162 void SkOpSegment::dumpAll() const {
1163     SkDebugf("%.*s", contour()->debugIndent(), "        ");
1164     this->dumpPts();
1165     const SkOpSpanBase* span = &fHead;
1166     contour()->indentDump();
1167     do {
1168         span->dumpAll();
1169     } while (!span->final() && (span = span->upCast()->next()));
1170     contour()->outdentDump();
1171 }
1172 
dumpAngles() const1173 void SkOpSegment::dumpAngles() const {
1174     SkDebugf("seg=%d\n", debugID());
1175     const SkOpSpanBase* span = &fHead;
1176     do {
1177         const SkOpAngle* fAngle = span->fromAngle();
1178         const SkOpAngle* tAngle = span->final() ? nullptr : span->upCast()->toAngle();
1179         if (fAngle) {
1180             SkDebugf("  span=%d from=%d ", span->debugID(), fAngle->debugID());
1181             fAngle->dumpTo(this, tAngle);
1182         }
1183         if (tAngle) {
1184             SkDebugf("  span=%d to=%d   ", span->debugID(), tAngle->debugID());
1185             tAngle->dumpTo(this, fAngle);
1186         }
1187     } while (!span->final() && (span = span->upCast()->next()));
1188 }
1189 
dumpCoin() const1190 void SkOpSegment::dumpCoin() const {
1191     const SkOpSpan* span = &fHead;
1192     do {
1193         span->dumpCoin();
1194     } while ((span = span->next()->upCastable()));
1195 }
1196 
dumpPtsInner(const char * prefix) const1197 void SkOpSegment::dumpPtsInner(const char* prefix) const {
1198     int last = SkPathOpsVerbToPoints(fVerb);
1199     SkDebugf("%s=%d {{", prefix, this->debugID());
1200     if (fVerb == SkPath::kConic_Verb) {
1201         SkDebugf("{");
1202     }
1203     int index = 0;
1204     do {
1205         SkDPoint::Dump(fPts[index]);
1206         SkDebugf(", ");
1207     } while (++index < last);
1208     SkDPoint::Dump(fPts[index]);
1209     SkDebugf("}}");
1210     if (fVerb == SkPath::kConic_Verb) {
1211         SkDebugf(", %1.9gf}", fWeight);
1212     }
1213 }
1214 
dumpPts(const char * prefix) const1215 void SkOpSegment::dumpPts(const char* prefix) const {
1216     dumpPtsInner(prefix);
1217     SkDebugf("\n");
1218 }
1219 
dump() const1220 void SkCoincidentSpans::dump() const {
1221     SkDebugf("- seg=%d span=%d ptT=%d ", fCoinPtTStart->segment()->debugID(),
1222         fCoinPtTStart->span()->debugID(), fCoinPtTStart->debugID());
1223     fCoinPtTStart->dumpBase();
1224     SkDebugf(" span=%d ptT=%d ", fCoinPtTEnd->span()->debugID(), fCoinPtTEnd->debugID());
1225     fCoinPtTEnd->dumpBase();
1226     if (fCoinPtTStart->segment()->operand()) {
1227         SkDebugf(" operand");
1228     }
1229     if (fCoinPtTStart->segment()->isXor()) {
1230         SkDebugf(" xor");
1231     }
1232     SkDebugf("\n");
1233     SkDebugf("+ seg=%d span=%d ptT=%d ", fOppPtTStart->segment()->debugID(),
1234         fOppPtTStart->span()->debugID(), fOppPtTStart->debugID());
1235     fOppPtTStart->dumpBase();
1236     SkDebugf(" span=%d ptT=%d ", fOppPtTEnd->span()->debugID(), fOppPtTEnd->debugID());
1237     fOppPtTEnd->dumpBase();
1238     if (fOppPtTStart->segment()->operand()) {
1239         SkDebugf(" operand");
1240     }
1241     if (fOppPtTStart->segment()->isXor()) {
1242         SkDebugf(" xor");
1243     }
1244     SkDebugf("\n");
1245 }
1246 
dump() const1247 void SkOpCoincidence::dump() const {
1248     SkCoincidentSpans* span = fHead;
1249     while (span) {
1250         span->dump();
1251         span = span->next();
1252     }
1253     if (!fTop || fHead == fTop) {
1254         return;
1255     }
1256     SkDebugf("top:\n");
1257     span = fTop;
1258     int count = 0;
1259     while (span) {
1260         span->dump();
1261         span = span->next();
1262         SkCoincidentSpans* check = fTop;
1263         ++count;
1264         for (int index = 0; index < count; ++index) {
1265             if (span == check) {
1266                 SkDebugf("(loops to #%d)\n", index);
1267                 return;
1268             }
1269             check = check->next();
1270         }
1271     }
1272 }
1273 
dump() const1274 void SkOpContour::dump() const {
1275     SkDebugf("contour=%d count=%d op=%d xor=%d\n", this->debugID(), fCount, fOperand, fXor);
1276     if (!fCount) {
1277         return;
1278     }
1279     const SkOpSegment* segment = &fHead;
1280     SkDEBUGCODE(fDebugIndent = 0);
1281     this->indentDump();
1282     do {
1283         segment->dump();
1284     } while ((segment = segment->next()));
1285     this->outdentDump();
1286 }
1287 
dumpAll() const1288 void SkOpContour::dumpAll() const {
1289     SkDebugf("contour=%d count=%d op=%d xor=%d\n", this->debugID(), fCount, fOperand, fXor);
1290     if (!fCount) {
1291         return;
1292     }
1293     const SkOpSegment* segment = &fHead;
1294     SkDEBUGCODE(fDebugIndent = 0);
1295     this->indentDump();
1296     do {
1297         segment->dumpAll();
1298     } while ((segment = segment->next()));
1299     this->outdentDump();
1300 }
1301 
1302 
dumpAngles() const1303 void SkOpContour::dumpAngles() const {
1304     SkDebugf("contour=%d\n", this->debugID());
1305     const SkOpSegment* segment = &fHead;
1306     do {
1307         SkDebugf("  seg=%d ", segment->debugID());
1308         segment->dumpAngles();
1309     } while ((segment = segment->next()));
1310 }
1311 
dumpPt(int index) const1312 void SkOpContour::dumpPt(int index) const {
1313     const SkOpSegment* segment = &fHead;
1314     do {
1315         if (segment->debugID() == index) {
1316             segment->dumpPts();
1317         }
1318     } while ((segment = segment->next()));
1319 }
1320 
dumpPts(const char * prefix) const1321 void SkOpContour::dumpPts(const char* prefix) const {
1322     SkDebugf("contour=%d\n", this->debugID());
1323     const SkOpSegment* segment = &fHead;
1324     do {
1325         SkDebugf("  %s=%d ", prefix, segment->debugID());
1326         segment->dumpPts(prefix);
1327     } while ((segment = segment->next()));
1328 }
1329 
dumpPtsX(const char * prefix) const1330 void SkOpContour::dumpPtsX(const char* prefix) const {
1331     if (!this->fCount) {
1332         SkDebugf("<empty>\n");
1333         return;
1334     }
1335     const SkOpSegment* segment = &fHead;
1336     do {
1337         segment->dumpPts(prefix);
1338     } while ((segment = segment->next()));
1339 }
1340 
dumpSegment(int index) const1341 void SkOpContour::dumpSegment(int index) const {
1342     debugSegment(index)->dump();
1343 }
1344 
dumpSegments(const char * prefix,SkPathOp op) const1345 void SkOpContour::dumpSegments(const char* prefix, SkPathOp op) const {
1346     bool firstOp = false;
1347     const SkOpContour* c = this;
1348     do {
1349         if (!firstOp && c->operand() && op >= 0) {
1350 #if DEBUG_ACTIVE_OP
1351             SkDebugf("op %s\n", SkPathOpsDebug::kPathOpStr[op]);
1352 #endif
1353             firstOp = true;
1354         }
1355         c->dumpPtsX(prefix);
1356     } while ((c = c->next()));
1357 }
1358 
dumpSpan(int index) const1359 void SkOpContour::dumpSpan(int index) const {
1360     debugSpan(index)->dump();
1361 }
1362 
dumpSpans() const1363 void SkOpContour::dumpSpans() const {
1364     SkDebugf("contour=%d\n", this->debugID());
1365     const SkOpSegment* segment = &fHead;
1366     do {
1367         SkDebugf("  seg=%d ", segment->debugID());
1368         segment->dump();
1369     } while ((segment = segment->next()));
1370 }
1371 
dump() const1372 void SkOpCurve::dump() const {
1373     int count = SkPathOpsVerbToPoints(SkDEBUGRELEASE(fVerb, SkPath::kCubic_Verb));
1374     SkDebugf("{{");
1375     int index;
1376     for (index = 0; index <= count - 1; ++index) {
1377         SkDebugf("{%1.9gf,%1.9gf}, ", fPts[index].fX, fPts[index].fY);
1378     }
1379     SkDebugf("{%1.9gf,%1.9gf}}}\n", fPts[index].fX, fPts[index].fY);
1380 }
1381 
1382 #ifdef SK_DEBUG
debugAngle(int id) const1383 const SkOpAngle* SkOpGlobalState::debugAngle(int id) const {
1384     const SkOpContour* contour = fContourHead;
1385     do {
1386         const SkOpSegment* segment = contour->first();
1387         while (segment) {
1388             const SkOpSpan* span = segment->head();
1389             do {
1390                 SkOpAngle* angle = span->fromAngle();
1391                 if (angle && angle->debugID() == id) {
1392                     return angle;
1393                 }
1394                 angle = span->toAngle();
1395                 if (angle && angle->debugID() == id) {
1396                     return angle;
1397                 }
1398             } while ((span = span->next()->upCastable()));
1399             const SkOpSpanBase* tail = segment->tail();
1400             SkOpAngle* angle = tail->fromAngle();
1401             if (angle && angle->debugID() == id) {
1402                 return angle;
1403             }
1404             segment = segment->next();
1405         }
1406     } while ((contour = contour->next()));
1407     return nullptr;
1408 }
1409 
debugContour(int id) const1410 SkOpContour* SkOpGlobalState::debugContour(int id) const {
1411     SkOpContour* contour = fContourHead;
1412     do {
1413         if (contour->debugID() == id) {
1414             return contour;
1415         }
1416     } while ((contour = contour->next()));
1417     return nullptr;
1418 }
1419 
debugPtT(int id) const1420 const SkOpPtT* SkOpGlobalState::debugPtT(int id) const {
1421     const SkOpContour* contour = fContourHead;
1422     do {
1423         const SkOpSegment* segment = contour->first();
1424         while (segment) {
1425             const SkOpSpan* span = segment->head();
1426             do {
1427                 const SkOpPtT* ptT = span->ptT();
1428                 if (ptT->debugMatchID(id)) {
1429                     return ptT;
1430                 }
1431             } while ((span = span->next()->upCastable()));
1432             const SkOpSpanBase* tail = segment->tail();
1433             const SkOpPtT* ptT = tail->ptT();
1434             if (ptT->debugMatchID(id)) {
1435                 return ptT;
1436             }
1437             segment = segment->next();
1438         }
1439     } while ((contour = contour->next()));
1440     return nullptr;
1441 }
1442 
debugSegment(int id) const1443 const SkOpSegment* SkOpGlobalState::debugSegment(int id) const {
1444     const SkOpContour* contour = fContourHead;
1445     do {
1446         const SkOpSegment* segment = contour->first();
1447         while (segment) {
1448             if (segment->debugID() == id) {
1449                 return segment;
1450             }
1451             segment = segment->next();
1452         }
1453     } while ((contour = contour->next()));
1454     return nullptr;
1455 }
1456 
debugSpan(int id) const1457 const SkOpSpanBase* SkOpGlobalState::debugSpan(int id) const {
1458     const SkOpContour* contour = fContourHead;
1459     do {
1460         const SkOpSegment* segment = contour->first();
1461         while (segment) {
1462             const SkOpSpan* span = segment->head();
1463             do {
1464                 if (span->debugID() == id) {
1465                     return span;
1466                 }
1467             } while ((span = span->next()->upCastable()));
1468             const SkOpSpanBase* tail = segment->tail();
1469             if (tail->debugID() == id) {
1470                 return tail;
1471             }
1472             segment = segment->next();
1473         }
1474     } while ((contour = contour->next()));
1475     return nullptr;
1476 }
1477 #endif
1478 
1479 #if DEBUG_T_SECT_DUMP > 1
1480 int gDumpTSectNum;
1481 #endif
1482