File: client_resource_provider.h

package info (click to toggle)
chromium 139.0.7258.127-1
  • links: PTS, VCS
  • area: main
  • in suites:
  • size: 6,122,068 kB
  • sloc: cpp: 35,100,771; ansic: 7,163,530; javascript: 4,103,002; python: 1,436,920; asm: 946,517; xml: 746,709; pascal: 187,653; perl: 88,691; sh: 88,436; objc: 79,953; sql: 51,488; cs: 44,583; fortran: 24,137; makefile: 22,147; tcl: 15,277; php: 13,980; yacc: 8,984; ruby: 7,485; awk: 3,720; lisp: 3,096; lex: 1,327; ada: 727; jsp: 228; sed: 36
file content (218 lines) | stat: -rw-r--r-- 9,679 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
// Copyright 2017 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef COMPONENTS_VIZ_CLIENT_CLIENT_RESOURCE_PROVIDER_H_
#define COMPONENTS_VIZ_CLIENT_CLIENT_RESOURCE_PROVIDER_H_

#include <memory>
#include <vector>

#include "base/containers/flat_map.h"
#include "base/functional/callback.h"
#include "base/memory/weak_ptr.h"
#include "base/task/sequenced_task_runner.h"
#include "base/threading/thread_checker.h"
#include "components/viz/client/viz_client_export.h"
#include "components/viz/common/display/renderer_settings.h"
#include "components/viz/common/resources/release_callback.h"
#include "components/viz/common/resources/resource_id.h"
#include "components/viz/common/resources/returned_resource.h"
#include "components/viz/common/resources/transferable_resource.h"
#include "third_party/khronos/GLES2/gl2.h"

namespace gpu {
namespace raster {
class RasterInterface;
}
}  // namespace gpu

namespace viz {
class RasterContextProvider;

// This class is used to give an integer name (ResourceId) to a gpu or software
// resource (shipped as a TransferableResource), in order to use that name in
// DrawQuads and give the resource to the viz display compositor. When the
// resource is removed from the ClientResourceProvider, the ReleaseCallback will
// be called once the resource is no longer in use by the display compositor.
//
// This class is not thread-safe and can only be called from the thread it was
// created on (in practice, the impl thread).
class VIZ_CLIENT_EXPORT ClientResourceProvider {
 public:
  using ResourceFlushCallback = base::RepeatingCallback<void()>;

  // Upon destruction this will call `batch_release_callback_` in order to
  // signal that all accumulated resource callbacks should be ran.
  //
  // See `CreateScopedBatchResourcesRelease`
  class VIZ_CLIENT_EXPORT ScopedBatchResourcesRelease {
   public:
    ScopedBatchResourcesRelease(const ScopedBatchResourcesRelease& other) =
        delete;
    ScopedBatchResourcesRelease& operator=(
        const ScopedBatchResourcesRelease& other) = delete;
    ScopedBatchResourcesRelease(ScopedBatchResourcesRelease&& other);
    ScopedBatchResourcesRelease& operator=(
        ScopedBatchResourcesRelease&& other) = default;
    ~ScopedBatchResourcesRelease();

   protected:
    explicit ScopedBatchResourcesRelease(
        base::OnceClosure batch_release_callback);

   private:
    base::OnceClosure batch_release_callback_;
  };

  ClientResourceProvider();
  ClientResourceProvider(
      scoped_refptr<base::SequencedTaskRunner> main_task_runner,
      scoped_refptr<base::SequencedTaskRunner> impl_task_runner,
      ResourceFlushCallback resource_flush_callback);

  ClientResourceProvider(const ClientResourceProvider&) = delete;
  ClientResourceProvider& operator=(const ClientResourceProvider&) = delete;

  ~ClientResourceProvider();

  static gpu::SyncToken GenerateSyncTokenHelper(
      gpu::raster::RasterInterface* ri);

  // Prepares resources to be transfered to the parent, moving them to
  // mailboxes and serializing meta-data into TransferableResources.
  // Resources are not removed from the ResourceProvider, but are marked as
  // "in use".
  void PrepareSendToParent(
      const std::vector<ResourceId>& resource_ids,
      std::vector<TransferableResource>* transferable_resources,
      RasterContextProvider* context_provider);

  // Receives resources from the parent, moving them from mailboxes. ResourceIds
  // passed are in the child namespace.
  // NOTE: if the sync_token is set on any TransferableResource, this will
  // wait on it.
  void ReceiveReturnsFromParent(
      std::vector<ReturnedResource> transferable_resources);

  // Receives a resource from an external client that can be used in compositor
  // frames, via the returned ResourceId. Can be provided with an optional
  // `evicted_callback`, which will be invoked once we are no longer visible and
  // have been evicted. When `evicted_callback` is called the client should
  // invoke `RemoveImportedResources` to unlock the resource. Allowing the
  // resource to be released when it is returned from the parent. When
  // `main_thread_release_callback` is provided, and
  // `features::kBatchMainThreadReleaseCallbacks` is enabled, the callback will
  // be invoked on `main_thread_task_runner_` when it has been returned.
  ResourceId ImportResource(const TransferableResource& resource,
                            ReleaseCallback impl_release_callback,
                            ReleaseCallback main_thread_release_callback = {},
                            ResourceEvictedCallback evicted_callback = {});
  // Removes an imported resource, which will call the ReleaseCallback given
  // originally, once the resource is no longer in use by any compositor frame.
  void RemoveImportedResource(ResourceId resource_id);

  // Call this to indicate that the connection to the parent is lost and
  // resources previously exported will not be able to be returned. If |lose| is
  // true, the resources are also marked as lost, to indicate the state of each
  // resource can not be known, and/or they can not be reused.
  //
  // When a resource is sent to the parent (via PrepareSendToParent) it is put
  // into an exported state, preventing it from being released until the parent
  // returns the resource. Calling this drops that exported state on all
  // resources allowing immediate release of them if they are removed via
  // RemoveImportedResource().
  void ReleaseAllExportedResources(bool lose);

  // Immediately runs the ReleaseCallback for all resources that have been
  // previously imported and removed, but not released yet. There should not be
  // any imported resources yet when this is called, as they can be removed
  // first via RemoveImportedResource(), and potentially avoid being lost.
  void ShutdownAndReleaseAllResources();

  // Verify that the ResourceId is valid and is known to this class, for debug
  // checks.
  void ValidateResource(ResourceId id) const;

  // Checks whether a resource is in use by a consumer.
  bool InUseByConsumer(ResourceId id);

  void SetEvicted(bool evicted);
  void SetVisible(bool visible);

  // Controls how `RemoveImportedResource` handled callbacks. While
  // `ScopedBatchResourcesRelease` is alive, we will collect all callbacks of
  // resources being removed. Upon leaving scope, we will perform a batch
  // release of all releases. This includes a single thread-hop to the
  // Main-thread for associated callbacks.
  ScopedBatchResourcesRelease CreateScopedBatchResourcesRelease();

  size_t num_resources_for_testing() const;

 private:
  struct ImportedResource;

  void PrepareSendToParentInternal(
      const std::vector<ResourceId>& export_ids,
      std::vector<TransferableResource>* list,
      base::OnceCallback<void(std::vector<GLbyte*>* tokens)>
          verify_sync_tokens);

  // Validates the memory impact of resources that are locked once we are both
  // evicted and no longer visible. This will also notify clients of eviction
  // via any `RemoveImportedResources`. If resources have been already returned
  // by the parent (the Display Compositor's FrameSink) this can lead to them
  // being returned to the client (such as cc::LayerTreeHostImpl.)
  void HandleEviction();

  void BatchMainReleaseCallbacks(
      std::vector<base::OnceClosure> release_callbacks);

  // Runs all release callbacks accumulated in `batch_main_release_callbacks_`.
  // Main thread callbacks will be posted to that thread in a single thread hop.
  void BatchResourceRelease();
  // If `batch` is true, then this will take the `main_thread_release_callback`
  // from `imported` to be batched later. Otherwise this runs them immediately.
  // This will also run all `impl_thread_release_callback` immediately.
  void TakeOrRunResourceReleases(bool batch, ImportedResource& imported);

  THREAD_CHECKER(thread_checker_);

  base::flat_map<ResourceId, ImportedResource> imported_resources_;
  // The ResourceIds in ClientResourceProvider start from 1 to avoid
  // conflicts with id from DisplayResourceProvider.
  ResourceIdGenerator id_generator_;

  // Whether the Client has had its Surface Evicted. When `true` all
  // `imported_resources_` are no longer required by the Parent. Though we need
  // to wait until we are not `visible_` as the Client may still use them.
  bool evicted_ = false;

  // Whether the Client is visible. While ClientResourceProvider is not
  // thread-safe, it is often used in a multi-threaded Renderer. While `true`
  // all `imported_resources_` may still be used by the Client. So it is not
  // safe to release them, even if we have been `evicted_`.
  bool visible_ = false;

  const scoped_refptr<base::SequencedTaskRunner> main_task_runner_;
  const scoped_refptr<base::SequencedTaskRunner> impl_task_runner_;

  ResourceFlushCallback resource_flush_callback_;

  // When true, we are able to use our TaskRunners to post all
  // `main_thread_release_callback` to the `main_task_runner_`. Enabling us to
  // have a single thread hop, rather than each callback performing it's own
  // separate hop.
  bool threaded_release_callbacks_supported_ = false;

  // While `true` resources being released will have their callbacks stored in
  // the vector below. To be released afterwards in `BatchResourceRelease`.
  bool batch_release_callbacks_ = false;
  std::vector<base::OnceClosure> batch_main_release_callbacks_;

  base::WeakPtrFactory<ClientResourceProvider> weak_factory_{this};
};

}  // namespace viz

#endif  // COMPONENTS_VIZ_CLIENT_CLIENT_RESOURCE_PROVIDER_H_