Deprecate GrDrawOp::fixedFunctionFlags()

Replaces this call with a usesMSAA() method that gets called before
finalize(), and usesStencil() which gets called after.

Bug: skia:12047
Change-Id: I860dc39e9af23a77f6ee1420d6bc648ab747b504
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/413356
Commit-Queue: Chris Dalton <csmartdalton@google.com>
Reviewed-by: Michael Ludwig <michaelludwig@google.com>
diff --git a/src/gpu/GrOpsTask.cpp b/src/gpu/GrOpsTask.cpp
index a387269..fd4bdf0 100644
--- a/src/gpu/GrOpsTask.cpp
+++ b/src/gpu/GrOpsTask.cpp
@@ -390,8 +390,7 @@
     this->recordOp(std::move(op), GrProcessorSet::EmptySetAnalysis(), nullptr, nullptr, caps);
 }
 
-void GrOpsTask::addDrawOp(GrDrawingManager* drawingMgr, GrOp::Owner op,
-                          GrDrawOp::FixedFunctionFlags fixedFunctionFlags,
+void GrOpsTask::addDrawOp(GrDrawingManager* drawingMgr, GrOp::Owner op, bool usesMSAA,
                           const GrProcessorSet::Analysis& processorAnalysis, GrAppliedClip&& clip,
                           const DstProxyView& dstProxyView,
                           GrTextureResolveManager textureResolveManager, const GrCaps& caps) {
@@ -424,12 +423,11 @@
 #ifdef SK_DEBUG
     // Ensure we can support dynamic msaa if the caller is trying to trigger it.
     GrRenderTargetProxy* rtProxy = this->target(0)->asRenderTargetProxy();
-    if (rtProxy->numSamples() == 1 &&
-        (fixedFunctionFlags & GrDrawOp::FixedFunctionFlags::kUsesHWAA)) {
+    if (rtProxy->numSamples() == 1 && usesMSAA) {
         SkASSERT(caps.supportsDynamicMSAA(rtProxy));
     }
 #endif
-    fUsesMSAASurface |= (fixedFunctionFlags & GrDrawOp::FixedFunctionFlags::kUsesHWAA);
+    fUsesMSAASurface |= usesMSAA;
 
     this->recordOp(std::move(op), processorAnalysis, clip.doesClip() ? &clip : nullptr,
                    &dstProxyView, caps);
diff --git a/src/gpu/GrOpsTask.h b/src/gpu/GrOpsTask.h
index 89b1576..0d308fa 100644
--- a/src/gpu/GrOpsTask.h
+++ b/src/gpu/GrOpsTask.h
@@ -71,9 +71,8 @@
 
     void addOp(GrDrawingManager*, GrOp::Owner, GrTextureResolveManager, const GrCaps&);
 
-    void addDrawOp(GrDrawingManager*, GrOp::Owner, GrDrawOp::FixedFunctionFlags,
-                   const GrProcessorSet::Analysis&, GrAppliedClip&&, const DstProxyView&,
-                   GrTextureResolveManager, const GrCaps&);
+    void addDrawOp(GrDrawingManager*, GrOp::Owner, bool usesMSAA, const GrProcessorSet::Analysis&,
+                   GrAppliedClip&&, const DstProxyView&, GrTextureResolveManager, const GrCaps&);
 
     void discard();
 
diff --git a/src/gpu/GrSurfaceDrawContext.cpp b/src/gpu/GrSurfaceDrawContext.cpp
index 06a53f1..9ca5319 100644
--- a/src/gpu/GrSurfaceDrawContext.cpp
+++ b/src/gpu/GrSurfaceDrawContext.cpp
@@ -1879,19 +1879,12 @@
     SkRect bounds;
     op_bounds(&bounds, op.get());
     GrAppliedClip appliedClip(this->dimensions(), this->asSurfaceProxy()->backingStoreDimensions());
-    GrDrawOp::FixedFunctionFlags fixedFunctionFlags = drawOp->fixedFunctionFlags();
-    bool usesHWAA = fixedFunctionFlags & GrDrawOp::FixedFunctionFlags::kUsesHWAA;
-    bool usesUserStencilBits = fixedFunctionFlags & GrDrawOp::FixedFunctionFlags::kUsesStencil;
-
-    if (usesUserStencilBits) {  // Stencil clipping will call setNeedsStencil on its own, if needed.
-        this->setNeedsStencil();
-    }
-
+    bool usesMSAA = drawOp->usesMSAA();
     bool skipDraw = false;
     if (clip) {
         // Have a complex clip, so defer to its early clip culling
         GrAAType aaType;
-        if (usesHWAA) {
+        if (usesMSAA) {
             aaType = GrAAType::kMSAA;
         } else {
             aaType = op->hasAABloat() ? GrAAType::kCoverage : GrAAType::kNone;
@@ -1920,13 +1913,19 @@
         }
     }
 
+    // Note if the op needs stencil. Stencil clipping already called setNeedsStencil for itself, if
+    // needed.
+    if (drawOp->usesStencil()) {
+        this->setNeedsStencil();
+    }
+
     auto opsTask = this->getOpsTask();
     if (willAddFn) {
         willAddFn(op.get(), opsTask->uniqueID());
     }
 
 #if GR_GPU_STATS && GR_TEST_UTILS
-    if (fCanUseDynamicMSAA && usesHWAA) {
+    if (fCanUseDynamicMSAA && usesMSAA) {
         if (!opsTask->usesMSAASurface()) {
             fContext->priv().dmsaaStats().fNumMultisampleRenderPasses++;
         }
@@ -1934,12 +1933,12 @@
     }
 #endif
 
-    opsTask->addDrawOp(this->drawingManager(), std::move(op), fixedFunctionFlags, analysis,
+    opsTask->addDrawOp(this->drawingManager(), std::move(op), usesMSAA, analysis,
                        std::move(appliedClip), dstProxyView,
                        GrTextureResolveManager(this->drawingManager()), *this->caps());
 
 #ifdef SK_DEBUG
-    if (fCanUseDynamicMSAA && usesHWAA) {
+    if (fCanUseDynamicMSAA && usesMSAA) {
         SkASSERT(opsTask->usesMSAASurface());
     }
 #endif
diff --git a/src/gpu/GrSurfaceFillContext.cpp b/src/gpu/GrSurfaceFillContext.cpp
index 8db2f86..0cf7b32 100644
--- a/src/gpu/GrSurfaceFillContext.cpp
+++ b/src/gpu/GrSurfaceFillContext.cpp
@@ -292,7 +292,7 @@
     auto clip = GrAppliedClip::Disabled();
     const GrCaps& caps = *this->caps();
     GrProcessorSet::Analysis analysis = op->finalize(caps, &clip, clampType);
-    SkASSERT(!(op->fixedFunctionFlags() & GrDrawOp::FixedFunctionFlags::kUsesStencil));
+    SkASSERT(!op->usesStencil());
     SkASSERT(!analysis.requiresDstTexture());
     SkRect bounds = owner->bounds();
     // We shouldn't have coverage AA or hairline draws in fill contexts.
@@ -306,7 +306,7 @@
     GrXferProcessor::DstProxyView dstProxyView;
     this->getOpsTask()->addDrawOp(fContext->priv().drawingManager(),
                                   std::move(owner),
-                                  op->fixedFunctionFlags(),
+                                  op->usesMSAA(),
                                   analysis,
                                   std::move(clip),
                                   dstProxyView,
diff --git a/src/gpu/ops/GrDrawOp.h b/src/gpu/ops/GrDrawOp.h
index 788e47c..ebcc9ae 100644
--- a/src/gpu/ops/GrDrawOp.h
+++ b/src/gpu/ops/GrDrawOp.h
@@ -23,18 +23,12 @@
     GrDrawOp(uint32_t classID) : INHERITED(classID) {}
 
     /**
-     * This information is required to determine how to compute a GrAppliedClip from a GrClip for
-     * this op.
+     * Called before setting up the GrAppliedClip and before finalize. This information is required
+     * to determine how to compute a GrAppliedClip from a GrClip for this op.
      */
-    enum class FixedFunctionFlags : uint32_t {
-        kNone = 0x0,
-        /** Indices that the op will enable MSAA. */
-        kUsesHWAA = 0x1,
-        /** Indices that the op reads and/or writes the stencil buffer */
-        kUsesStencil = 0x2,
-    };
-    GR_DECL_BITFIELD_CLASS_OPS_FRIENDS(FixedFunctionFlags);
-    virtual FixedFunctionFlags fixedFunctionFlags() const = 0;
+    virtual bool usesMSAA() const {
+        return this->fixedFunctionFlags() & FixedFunctionFlags::kUsesHWAA;
+    }
 
     /**
      * This is called after the GrAppliedClip has been computed and just prior to recording the op
@@ -45,6 +39,13 @@
      */
     virtual GrProcessorSet::Analysis finalize(const GrCaps&, const GrAppliedClip*, GrClampType) = 0;
 
+    /**
+     * Called after finalize, at which point every op should know whether it will need stencil.
+     */
+    virtual bool usesStencil() const {
+        return this->fixedFunctionFlags() & FixedFunctionFlags::kUsesStencil;
+    }
+
 #ifdef SK_DEBUG
     bool fAddDrawOpCalled = false;
 
@@ -58,7 +59,28 @@
     virtual int numQuads() const { return -1; }
 #endif
 
+protected:
+    /**
+     * DEPRECATED: This is a legacy implementation for usesMSAA() and usesStencil(). Newer ops
+     * should override those methods directly.
+     */
+    enum class FixedFunctionFlags : uint32_t {
+        kNone = 0x0,
+        /** Indices that the op will enable MSAA. */
+        kUsesHWAA = 0x1,
+        /** Indices that the op reads and/or writes the stencil buffer */
+        kUsesStencil = 0x2,
+    };
+    GR_DECL_BITFIELD_CLASS_OPS_FRIENDS(FixedFunctionFlags);
+    virtual FixedFunctionFlags fixedFunctionFlags() const {
+        // Override usesMSAA() and usesStencil() instead.
+        SK_ABORT("fixedFunctionFlags() not implemented.");
+    }
+
 private:
+    friend class GrSimpleMeshDrawOpHelper;  // For FixedFunctionFlags.
+    friend class GrSimpleMeshDrawOpHelperWithStencil;  // For FixedFunctionFlags.
+
     using INHERITED = GrOp;
 };