Make AAStrokeRectOp compatible with DMSAA

Extends the outsets and insets in order to guarantee a full sample
mask on pixels with partial coverage. Due to skia:12206, we only
render miter stroks this way when using DMSAA.

Bug: skia:11396
Bug: skia:12206
Change-Id: I2d429b59a781d59861cd2fd2ee008076ec6e1e27
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/428016
Commit-Queue: Chris Dalton <csmartdalton@google.com>
Reviewed-by: Brian Salomon <bsalomon@google.com>
diff --git a/src/gpu/GrDefaultGeoProcFactory.cpp b/src/gpu/GrDefaultGeoProcFactory.cpp
index e306ed4..d27192f 100644
--- a/src/gpu/GrDefaultGeoProcFactory.cpp
+++ b/src/gpu/GrDefaultGeoProcFactory.cpp
@@ -23,11 +23,12 @@
  */
 
 enum GPFlag {
-    kColorAttribute_GPFlag          = 0x1,
-    kColorAttributeIsWide_GPFlag    = 0x2,
-    kLocalCoordAttribute_GPFlag     = 0x4,
-    kCoverageAttribute_GPFlag       = 0x8,
-    kCoverageAttributeTweak_GPFlag  = 0x10,
+    kColorAttribute_GPFlag              = 0x1,
+    kColorAttributeIsWide_GPFlag        = 0x2,
+    kLocalCoordAttribute_GPFlag         = 0x4,
+    kCoverageAttribute_GPFlag           = 0x8,
+    kCoverageAttributeTweak_GPFlag      = 0x10,
+    kCoverageAttributeUnclamped_GPFlag  = 0x20,
 };
 
 class DefaultGeoProc : public GrGeometryProcessor {
@@ -74,7 +75,9 @@
             varyingHandler->emitAttributes(gp);
 
             bool tweakAlpha = SkToBool(gp.fFlags & kCoverageAttributeTweak_GPFlag);
+            bool coverageNeedsSaturate = SkToBool(gp.fFlags & kCoverageAttributeUnclamped_GPFlag);
             SkASSERT(!tweakAlpha || gp.hasVertexCoverage());
+            SkASSERT(!tweakAlpha || !coverageNeedsSaturate);
 
             // Setup pass through color
             fragBuilder->codeAppendf("half4 %s;", args.fOutputColor);
@@ -133,7 +136,12 @@
             if (gp.hasVertexCoverage() && !tweakAlpha) {
                 fragBuilder->codeAppendf("half alpha = 1.0;");
                 varyingHandler->addPassThroughAttribute(gp.fInCoverage, "alpha");
-                fragBuilder->codeAppendf("half4 %s = half4(alpha);", args.fOutputCoverage);
+                if (coverageNeedsSaturate) {
+                    fragBuilder->codeAppendf("half4 %s = half4(saturate(alpha));",
+                                             args.fOutputCoverage);
+                } else {
+                    fragBuilder->codeAppendf("half4 %s = half4(alpha);", args.fOutputCoverage);
+                }
             } else if (gp.coverage() == 0xff) {
                 fragBuilder->codeAppendf("const half4 %s = half4(1);", args.fOutputCoverage);
             } else {
@@ -268,7 +276,8 @@
     if (d->fRandom->nextBool()) {
         flags |= kCoverageAttribute_GPFlag;
         if (d->fRandom->nextBool()) {
-            flags |= kCoverageAttributeTweak_GPFlag;
+            flags |= (d->fRandom->nextBool()) ? kCoverageAttributeTweak_GPFlag
+                                              : kCoverageAttributeUnclamped_GPFlag;
         }
     }
     if (d->fRandom->nextBool()) {
@@ -305,6 +314,8 @@
         flags |= kCoverageAttribute_GPFlag;
     } else if (Coverage::kAttributeTweakAlpha_Type == coverage.fType) {
         flags |= kCoverageAttribute_GPFlag | kCoverageAttributeTweak_GPFlag;
+    } else if (Coverage::kAttributeUnclamped_Type == coverage.fType) {
+        flags |= kCoverageAttribute_GPFlag | kCoverageAttributeUnclamped_GPFlag;
     }
     flags |= localCoords.fType == LocalCoords::kHasExplicit_Type ? kLocalCoordAttribute_GPFlag : 0;