Remove support for non-AA in the tessellation atlas

Now that multisampleDisableSupport is completely turned off, this
won't change any behavior.

Change-Id: I3fe0518aee5321c7c92ac0b4b77333e910f08ce6
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/431076
Commit-Queue: Chris Dalton <csmartdalton@google.com>
Reviewed-by: Michael Ludwig <michaelludwig@google.com>
diff --git a/src/gpu/GrClipStack.cpp b/src/gpu/GrClipStack.cpp
index 7472c27..3a4affa 100644
--- a/src/gpu/GrClipStack.cpp
+++ b/src/gpu/GrClipStack.cpp
@@ -240,6 +240,9 @@
                                 const SkIRect& scissorBounds,
                                 const GrClipStack::Element& e,
                                 std::unique_ptr<GrFragmentProcessor> inputFP) {
+    if (e.fAA != GrAA::kYes) {
+        return GrFPFailure(std::move(inputFP));
+    }
     SkPath path;
     e.fShape.asPath(&path);
     SkASSERT(!path.isInverseFillType());
@@ -248,7 +251,7 @@
         path.toggleInverseFillType();
     }
     return tessellator->makeAtlasClipFP(rContext, opBeingClipped, std::move(inputFP), scissorBounds,
-                                        e.fLocalToDevice, path, e.fAA);
+                                        e.fLocalToDevice, path);
 }
 
 static void draw_to_sw_mask(GrSWMaskHelper* helper, const GrClipStack::Element& e, bool clearMask) {
diff --git a/src/gpu/tessellate/GrAtlasRenderTask.cpp b/src/gpu/tessellate/GrAtlasRenderTask.cpp
index 5d9f404..0918b83 100644
--- a/src/gpu/tessellate/GrAtlasRenderTask.cpp
+++ b/src/gpu/tessellate/GrAtlasRenderTask.cpp
@@ -25,7 +25,7 @@
         , fDynamicAtlas(std::move(dynamicAtlas)) {
 }
 
-bool GrAtlasRenderTask::addPath(const SkMatrix& viewMatrix, const SkPath& path, bool antialias,
+bool GrAtlasRenderTask::addPath(const SkMatrix& viewMatrix, const SkPath& path,
                                 SkIPoint pathDevTopLeft, int widthInAtlas, int heightInAtlas,
                                 bool transposedInAtlas, SkIPoint16* locationInAtlas) {
     SkASSERT(!this->isClosed());
@@ -48,8 +48,8 @@
                                         locationInAtlas->y() - pathDevTopLeft.y());
     }
 
-    // Concatenate this path onto our uber path that matches its fill and AA types.
-    SkPath* uberPath = this->getUberPath(path.getFillType(), antialias);
+    // Concatenate this path onto our uber path that matches its fill rule.
+    SkPath* uberPath = this->getUberPath(GrFillRuleForSkPath(path));
     uberPath->moveTo(locationInAtlas->x(), locationInAtlas->y());  // Implicit moveTo(0,0).
     uberPath->addPath(path, pathToAtlasMatrix);
     return true;
@@ -89,19 +89,17 @@
     }
 
     // Add ops to stencil the atlas paths.
-    for (auto antialias : {false, true}) {
-        for (auto fillType : {SkPathFillType::kWinding, SkPathFillType::kEvenOdd}) {
-            SkPath* uberPath = this->getUberPath(fillType, antialias);
-            if (uberPath->isEmpty()) {
-                continue;
-            }
-            uberPath->setFillType(fillType);
-            GrAAType aaType = (antialias) ? GrAAType::kMSAA : GrAAType::kNone;
-            auto op = GrOp::Make<GrPathStencilCoverOp>(
-                    rContext, SkMatrix::I(), *uberPath, GrPaint(), aaType,
-                    GrTessellationPathRenderer::PathFlags::kStencilOnly, drawRect);
-            this->addAtlasDrawOp(std::move(op), antialias, caps);
+    for (auto fillRule : {GrFillRule::kNonzero, GrFillRule::kEvenOdd}) {
+        SkPath* uberPath = this->getUberPath(fillRule);
+        if (uberPath->isEmpty()) {
+            continue;
         }
+        uberPath->setFillType(fillRule == GrFillRule::kNonzero ? SkPathFillType::kWinding
+                                                               : SkPathFillType::kEvenOdd);
+        auto op = GrOp::Make<GrPathStencilCoverOp>(
+                rContext, SkMatrix::I(), *uberPath, GrPaint(), GrAAType::kMSAA,
+                GrTessellationPathRenderer::PathFlags::kStencilOnly, drawRect);
+        this->addAtlasDrawOp(std::move(op), caps);
     }
 
     // Finally, draw a fullscreen rect to cover our stencilled paths.
@@ -152,10 +150,10 @@
     GrQuad quad(rect);
     DrawQuad drawQuad{quad, quad, GrQuadAAFlags::kAll};
     auto op = GrFillRectOp::Make(rContext, std::move(paint), GrAAType::kMSAA, &drawQuad, stencil);
-    this->addAtlasDrawOp(std::move(op), true/*usesMSAA*/, *rContext->priv().caps());
+    this->addAtlasDrawOp(std::move(op), *rContext->priv().caps());
 }
 
-void GrAtlasRenderTask::addAtlasDrawOp(GrOp::Owner op, bool usesMSAA, const GrCaps& caps) {
+void GrAtlasRenderTask::addAtlasDrawOp(GrOp::Owner op, const GrCaps& caps) {
     SkASSERT(!this->isClosed());
 
     auto drawOp = static_cast<GrDrawOp*>(op.get());
@@ -167,7 +165,7 @@
     SkASSERT(!processorAnalysis.usesNonCoherentHWBlending());
 
     drawOp->setClippedBounds(drawOp->bounds());
-    this->recordOp(std::move(op), usesMSAA, processorAnalysis, nullptr, nullptr, caps);
+    this->recordOp(std::move(op), true/*usesMSAA*/, processorAnalysis, nullptr, nullptr, caps);
 }
 
 bool GrAtlasRenderTask::onExecute(GrOpFlushState* flushState) {
diff --git a/src/gpu/tessellate/GrAtlasRenderTask.h b/src/gpu/tessellate/GrAtlasRenderTask.h
index 4834ea4..1d679f2 100644
--- a/src/gpu/tessellate/GrAtlasRenderTask.h
+++ b/src/gpu/tessellate/GrAtlasRenderTask.h
@@ -32,9 +32,8 @@
     // Allocates a rectangle for, and stages the given path to be rendered into the atlas. Returns
     // false if there was not room in the atlas. On success, writes out the location of the path's
     // upper-left corner to 'locationInAtlas'.
-    bool addPath(const SkMatrix&, const SkPath&, bool antialias, SkIPoint pathDevTopLeft,
-                 int widthInAtlas, int heightInAtlas, bool transposedInAtlas,
-                 SkIPoint16* locationInAtlas);
+    bool addPath(const SkMatrix&, const SkPath&, SkIPoint pathDevTopLeft, int widthInAtlas,
+                 int heightInAtlas, bool transposedInAtlas, SkIPoint16* locationInAtlas);
 
     // Must be called at flush time. The texture proxy is instantiated with 'backingTexture', if
     // provided. See GrDynamicAtlas.
@@ -50,19 +49,17 @@
 
     void stencilAtlasRect(GrRecordingContext*, const SkRect&, const SkPMColor4f&,
                           const GrUserStencilSettings*);
-    void addAtlasDrawOp(GrOp::Owner, bool usesMSAA, const GrCaps&);
+    void addAtlasDrawOp(GrOp::Owner, const GrCaps&);
 
     // Executes the GrOpsTask and resolves msaa if needed.
     bool onExecute(GrOpFlushState* flushState) override;
 
-    SkPath* getUberPath(SkPathFillType fillType, bool antialias) {
-        int idx = (int)antialias << 1;
-        idx |= (int)fillType & 1;
-        return &fUberPaths[idx];
+    SkPath* getUberPath(GrFillRule fillRule) {
+        return &fUberPaths[fillRule == GrFillRule::kEvenOdd];
     }
 
     const std::unique_ptr<GrDynamicAtlas> fDynamicAtlas;
-    SkPath fUberPaths[4];  // 2 fillTypes * 2 antialias modes.
+    SkPath fUberPaths[2];  // 2 fill rules: "nonzero" and "even/odd".
 };
 
 #endif
diff --git a/src/gpu/tessellate/GrTessellationPathRenderer.cpp b/src/gpu/tessellate/GrTessellationPathRenderer.cpp
index be3a73b..9df42a9 100644
--- a/src/gpu/tessellate/GrTessellationPathRenderer.cpp
+++ b/src/gpu/tessellate/GrTessellationPathRenderer.cpp
@@ -145,7 +145,7 @@
         return true;
     }
 
-    if (args.fUserStencilSettings->isUnused()) {
+    if (args.fUserStencilSettings->isUnused() && args.fAAType == GrAAType::kMSAA) {
         // See if the path is small and simple enough to atlas instead of drawing directly.
         //
         // NOTE: The atlas uses alpha8 coverage even for msaa render targets. We could theoretically
@@ -163,8 +163,8 @@
             }
         };
         if (this->tryAddPathToAtlas(args.fContext, *args.fViewMatrix, path, pathDevBounds,
-                                    args.fAAType != GrAAType::kNone, &devIBounds, &locationInAtlas,
-                                    &transposedInAtlas, visitProxiesUsedByDraw)) {
+                                    &devIBounds, &locationInAtlas, &transposedInAtlas,
+                                    visitProxiesUsedByDraw)) {
             const GrCaps& caps = *args.fSurfaceDrawContext->caps();
             const SkIRect& fillBounds = path.isInverseFillType()
                     ? (args.fClip
@@ -245,7 +245,7 @@
                                                        std::unique_ptr<GrFragmentProcessor> inputFP,
                                                        const SkIRect& drawBounds,
                                                        const SkMatrix& viewMatrix,
-                                                       const SkPath& path, GrAA aa) {
+                                                       const SkPath& path) {
     if (viewMatrix.hasPerspective()) {
         return GrFPFailure(std::move(inputFP));
     }
@@ -264,9 +264,8 @@
         }
     };
     // tryAddPathToAtlas() ignores inverseness of the fill. See getAtlasUberPath().
-    if (!this->tryAddPathToAtlas(rContext, viewMatrix, path, pathDevBounds, aa != GrAA::kNo,
-                                 &devIBounds, &locationInAtlas, &transposedInAtlas,
-                                 visitProxiesUsedByDraw)) {
+    if (!this->tryAddPathToAtlas(rContext, viewMatrix, path, pathDevBounds, &devIBounds,
+                                 &locationInAtlas, &transposedInAtlas, visitProxiesUsedByDraw)) {
         // The path is too big, or the atlas ran out of room.
         return GrFPFailure(std::move(inputFP));
     }
@@ -296,9 +295,9 @@
                                                                    atlasMatrix, devIBounds));
 }
 
-void GrTessellationPathRenderer::AtlasPathKey::set(const SkMatrix& m, bool antialias,
-                                                   const SkPath& path) {
+void GrTessellationPathRenderer::AtlasPathKey::set(const SkMatrix& m, const SkPath& path) {
     using grvx::float2;
+    fPathGenID = path.getGenerationID();
     fAffineMatrix[0] = m.getScaleX();
     fAffineMatrix[1] = m.getSkewX();
     fAffineMatrix[2] = m.getSkewY();
@@ -308,14 +307,12 @@
     float2 subpixelPositionKey = skvx::trunc(subpixelPosition *
                                              GrTessellationShader::kLinearizationPrecision);
     skvx::cast<uint8_t>(subpixelPositionKey).store(fSubpixelPositionKey);
-    fAntialias = antialias;
-    fFillRule = (uint8_t)GrFillRuleForSkPath(path);  // Fill rule doesn't affect the path's genID.
-    fPathGenID = path.getGenerationID();
+    fFillRule = (uint16_t)GrFillRuleForSkPath(path);  // Fill rule doesn't affect the path's genID.
 }
 
 bool GrTessellationPathRenderer::tryAddPathToAtlas(GrRecordingContext* rContext,
                                                    const SkMatrix& viewMatrix, const SkPath& path,
-                                                   const SkRect& pathDevBounds, bool antialias,
+                                                   const SkRect& pathDevBounds,
                                                    SkIRect* devIBounds, SkIPoint16* locationInAtlas,
                                                    bool* transposedInAtlas,
                                                    const VisitProxiesFn& visitProxiesUsedByDraw) {
@@ -330,11 +327,6 @@
     // The atlas is not compatible with DDL. We should only be using it on direct contexts.
     SkASSERT(rContext->asDirectContext());
 
-    const GrCaps& caps = *rContext->priv().caps();
-    if (!caps.multisampleDisableSupport() && !antialias) {
-        return false;
-    }
-
     pathDevBounds.roundOut(devIBounds);
     int widthInAtlas = devIBounds->width();
     int heightInAtlas = devIBounds->height();
@@ -367,7 +359,7 @@
     // Check if this path is already in the atlas. This is mainly for clip paths.
     AtlasPathKey atlasPathKey;
     if (!path.isVolatile()) {
-        atlasPathKey.set(viewMatrix, antialias, path);
+        atlasPathKey.set(viewMatrix, path);
         if (const SkIPoint16* existingLocation = fAtlasPathCache.find(atlasPathKey)) {
             *locationInAtlas = *existingLocation;
             return true;
@@ -375,9 +367,8 @@
     }
 
     if (fAtlasRenderTasks.empty() ||
-        !fAtlasRenderTasks.back()->addPath(viewMatrix, path, antialias, devIBounds->topLeft(),
-                                           widthInAtlas, heightInAtlas, *transposedInAtlas,
-                                           locationInAtlas)) {
+        !fAtlasRenderTasks.back()->addPath(viewMatrix, path, devIBounds->topLeft(), widthInAtlas,
+                                           heightInAtlas, *transposedInAtlas, locationInAtlas)) {
         // We either don't have an atlas yet or the current one is full. Try to replace it.
         GrAtlasRenderTask* currentAtlasTask = (!fAtlasRenderTasks.empty())
                 ? fAtlasRenderTasks.back().get() : nullptr;
@@ -407,9 +398,8 @@
                                                           sk_make_sp<GrArenas>(),
                                                           std::move(dynamicAtlas));
         rContext->priv().drawingManager()->addAtlasTask(newAtlasTask, currentAtlasTask);
-        SkAssertResult(newAtlasTask->addPath(viewMatrix, path, antialias, devIBounds->topLeft(),
-                                             widthInAtlas, heightInAtlas, *transposedInAtlas,
-                                             locationInAtlas));
+        SkAssertResult(newAtlasTask->addPath(viewMatrix, path, devIBounds->topLeft(), widthInAtlas,
+                                             heightInAtlas, *transposedInAtlas, locationInAtlas));
         fAtlasRenderTasks.push_back(std::move(newAtlasTask));
         fAtlasPathCache.reset();
     }
diff --git a/src/gpu/tessellate/GrTessellationPathRenderer.h b/src/gpu/tessellate/GrTessellationPathRenderer.h
index f54121d..e5bf415 100644
--- a/src/gpu/tessellate/GrTessellationPathRenderer.h
+++ b/src/gpu/tessellate/GrTessellationPathRenderer.h
@@ -47,8 +47,8 @@
     bool onDrawPath(const DrawPathArgs&) override;
     void onStencilPath(const StencilPathArgs&) override;
 
-    // Returns a fragment processor that modulates inputFP by the given deviceSpacePath's coverage,
-    // implemented using an internal atlas.
+    // Returns an antialiased fragment processor that modulates inputFP by the given
+    // deviceSpacePath's coverage, implemented using an internal atlas. Non-aa is not supported.
     //
     // Returns 'inputFP' wrapped in GrFPFailure() if the path was too large, or if the current atlas
     // is full and already used by either opBeingClipped or inputFP. (Currently, "too large" means
@@ -57,7 +57,7 @@
     // Also returns GrFPFailure() if the view matrix has perspective.
     GrFPResult makeAtlasClipFP(GrRecordingContext*, const GrOp* opBeingClipped,
                                std::unique_ptr<GrFragmentProcessor> inputFP,
-                               const SkIRect& drawBounds, const SkMatrix&, const SkPath&, GrAA);
+                               const SkIRect& drawBounds, const SkMatrix&, const SkPath&);
 
     void preFlush(GrOnFlushResourceProvider*, SkSpan<const uint32_t> taskIDs) override;
 
@@ -70,7 +70,7 @@
     // in use according to 'visitProxiesUsedByDraw'. (Currently, "too large" means more than 128*128
     // total pixels, or larger than the atlas size in either dimension.)
     bool tryAddPathToAtlas(GrRecordingContext*, const SkMatrix&, const SkPath&,
-                           const SkRect& pathDevBounds, bool antialias, SkIRect* devIBounds,
+                           const SkRect& pathDevBounds, SkIRect* devIBounds,
                            SkIPoint16* locationInAtlas, bool* transposedInAtlas,
                            const VisitProxiesFn& visitProxiesUsedByDraw);
 
@@ -84,16 +84,15 @@
     // This simple cache remembers the locations of cacheable path masks in the most recent atlas.
     // Its main motivation is for clip paths.
     struct AtlasPathKey {
-        void set(const SkMatrix&, bool antialias, const SkPath&);
+        void set(const SkMatrix&, const SkPath&);
         bool operator==(const AtlasPathKey& k) const {
             static_assert(sizeof(*this) == sizeof(uint32_t) * 6);
             return !memcmp(this, &k, sizeof(*this));
         }
+        uint32_t fPathGenID;
         float fAffineMatrix[4];
         uint8_t fSubpixelPositionKey[2];
-        uint8_t fAntialias;
-        uint8_t fFillRule;
-        uint32_t fPathGenID;
+        uint16_t fFillRule;
     };
     SkTHashMap<AtlasPathKey, SkIPoint16> fAtlasPathCache;
 };