1/*
2 * Copyright 2020 Google LLC
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#ifndef GrUnrefDDLTask_DEFINED
9#define GrUnrefDDLTask_DEFINED
10
11#include "src/gpu/GrRenderTask.h"
12
13/** When a DDL is played back, the drawing manager refs the DDL and adds one
14 * of these to the DAG to release it after the flush. Thus the user is free
15 * to unref the DDL at their leisure without messing us up.
16 */
17class GrUnrefDDLTask final : public GrRenderTask {
18public:
19 GrUnrefDDLTask(sk_sp<const SkDeferredDisplayList> ddl)
20 : GrRenderTask()
21 , fDDL(std::move(ddl)) {}
22
23 // We actually do the unreffing in dtor instead of onExecute, so that we maintain the invariant
24 // that DDLs are always the last owners of their render tasks (because those tasks depend on
25 // memory owned by the DDL.) If we had this in onExecute, the tasks would still be alive in
26 // the drawing manager although it would already have executed them.
27 ~GrUnrefDDLTask() override {
28 fDDL.reset();
29 }
30
31private:
32 bool onIsUsed(GrSurfaceProxy* proxy) const override { return false; }
33 void handleInternalAllocationFailure() override {}
34 void gatherProxyIntervals(GrResourceAllocator* alloc) const override {
35 // We don't have any proxies, but the resource allocator will still bark
36 // if a task doesn't claim any op indices, so we oblige it.
37 alloc->incOps();
38 }
39
40 ExpectedOutcome onMakeClosed(const GrCaps&, SkIRect*) override {
41 return ExpectedOutcome::kTargetUnchanged;
42 }
43
44 bool onExecute(GrOpFlushState*) override { return true; }
45
46#if GR_TEST_UTILS
47 const char* name() const final { return "UnrefDDL"; }
48#endif
49#ifdef SK_DEBUG
50 void visitProxies_debugOnly(const GrOp::VisitProxyFunc& fn) const override {}
51#endif
52
53 sk_sp<const SkDeferredDisplayList> fDDL;
54};
55
56#endif
57