Flutter Impeller
hardware_buffer.h
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef FLUTTER_IMPELLER_TOOLKIT_ANDROID_HARDWARE_BUFFER_H_
6 #define FLUTTER_IMPELLER_TOOLKIT_ANDROID_HARDWARE_BUFFER_H_
7 
8 #include <optional>
9 
10 #include "flutter/fml/unique_fd.h"
11 #include "flutter/fml/unique_object.h"
12 #include "impeller/base/mask.h"
13 #include "impeller/geometry/size.h"
15 
16 namespace impeller::android {
17 
19  //----------------------------------------------------------------------------
20  /// This format is guaranteed to be supported on all versions of Android. This
21  /// format can also be converted to an Impeller and Vulkan format.
22  ///
23  /// @see Vulkan Format: VK_FORMAT_R8G8B8A8_UNORM
24  /// @see OpenGL ES Format: GL_RGBA8
25  ///
26  /// Why have many format when one format do trick?
27  ///
29 };
30 
32  kNone = 0u,
33  kFrameBufferAttachment = 1u << 0u,
34  kCompositorOverlay = 1u << 1u,
35  kSampledImage = 1u << 2u,
36  kCPUReadRarely = 1u << 3u,
37  kCPUReadOften = 1u << 4u,
38  kCPUWriteRarely = 1u << 5u,
39  kCPUWriteOften = 1u << 6u,
40 };
41 
43 
44 //------------------------------------------------------------------------------
45 /// @brief A descriptor use to specify hardware buffer allocations.
46 ///
51 
52  //----------------------------------------------------------------------------
53  /// @brief Create a descriptor of the given size that is suitable for use
54  /// as a swapchain image.
55  ///
56  /// @warning Descriptors of zero size are not allocatable. The next best
57  /// valid size is picked. So make sure to check the actual size of
58  /// the descriptor after this call is made to determine the size
59  /// of the allocated hardware buffer.
60  ///
61  /// @param[in] size The size. See the restrictions about valid sizes above.
62  ///
63  /// @return The hardware buffer descriptor.
64  ///
66 
67  //----------------------------------------------------------------------------
68  /// @brief If hardware buffers can be created using this descriptor.
69  /// Allocatable descriptors may still cause failing allocations in
70  /// case of resource exhaustion.
71  ///
72  /// @return `true` if allocatable (unless resource exhaustion).
73  ///
74  bool IsAllocatable() const;
75 
76  constexpr bool operator==(const HardwareBufferDescriptor& o) const = default;
77 };
78 
79 //------------------------------------------------------------------------------
80 /// @brief A wrapper for AHardwareBuffer
81 /// https://developer.android.com/ndk/reference/group/a-hardware-buffer
82 ///
83 /// This wrapper creates and owns a handle to a managed hardware
84 /// buffer. That is, there is no ability to take a reference to an
85 /// externally created hardware buffer.
86 ///
87 /// This wrapper is only available on Android API 29 and above.
88 ///
90  public:
91  static bool IsAvailableOnPlatform();
92 
93  explicit HardwareBuffer(HardwareBufferDescriptor descriptor);
94 
96 
97  HardwareBuffer(const HardwareBuffer&) = delete;
98 
100 
101  bool IsValid() const;
102 
103  AHardwareBuffer* GetHandle() const;
104 
106 
107  const AHardwareBuffer_Desc& GetAndroidDescriptor() const;
108 
109  static std::optional<AHardwareBuffer_Desc> Describe(AHardwareBuffer* buffer);
110 
111  //----------------------------------------------------------------------------
112  /// @brief Get the system wide unique ID of the hardware buffer if
113  /// possible. This is only available on Android API 31 and above.
114  /// Within the process, the handle are unique.
115  ///
116  /// @return The system unique id if one can be obtained.
117  ///
118  std::optional<uint64_t> GetSystemUniqueID() const;
119 
120  //----------------------------------------------------------------------------
121  /// @brief Get the system wide unique ID of the hardware buffer if
122  /// possible. This is only available on Android API 31 and above.
123  /// Within the process, the handle are unique.
124  ///
125  /// @return The system unique id if one can be obtained.
126  ///
127  static std::optional<uint64_t> GetSystemUniqueID(AHardwareBuffer* buffer);
128 
129  enum class CPUAccessType {
130  kRead,
131  kWrite,
132  };
133  //----------------------------------------------------------------------------
134  /// @brief Lock the buffer for CPU access. This call may fail if the
135  /// buffer was not created with one the usages that allow for CPU
136  /// access.
137  ///
138  /// @param[in] type The type
139  ///
140  /// @return A host-accessible buffer if there was no error related to
141  /// usage or buffer validity.
142  ///
143  void* Lock(CPUAccessType type) const;
144 
145  //----------------------------------------------------------------------------
146  /// @brief Unlock a mapping previously locked for CPU access.
147  ///
148  /// @return If the unlock was successful.
149  ///
150  bool Unlock() const;
151 
152  private:
153  struct UniqueAHardwareBufferTraits {
154  static AHardwareBuffer* InvalidValue() { return nullptr; }
155 
156  static bool IsValid(AHardwareBuffer* value) {
157  return value != InvalidValue();
158  }
159 
160  static void Free(AHardwareBuffer* value) {
161  GetProcTable().AHardwareBuffer_release(value);
162  }
163  };
164 
165  const HardwareBufferDescriptor descriptor_;
166  const AHardwareBuffer_Desc android_descriptor_;
167  fml::UniqueObject<AHardwareBuffer*, UniqueAHardwareBufferTraits> buffer_;
168  bool is_valid_ = false;
169 };
170 
171 } // namespace impeller::android
172 
173 namespace impeller {
174 
176 
177 } // namespace impeller
178 
179 #endif // FLUTTER_IMPELLER_TOOLKIT_ANDROID_HARDWARE_BUFFER_H_
GLenum type
A wrapper for AHardwareBuffer https://developer.android.com/ndk/reference/group/a-hardware-buffer.
HardwareBuffer(HardwareBufferDescriptor descriptor)
const HardwareBufferDescriptor & GetDescriptor() const
AHardwareBuffer * GetHandle() const
const AHardwareBuffer_Desc & GetAndroidDescriptor() const
HardwareBuffer & operator=(const HardwareBuffer &)=delete
bool Unlock() const
Unlock a mapping previously locked for CPU access.
static std::optional< AHardwareBuffer_Desc > Describe(AHardwareBuffer *buffer)
HardwareBuffer(const HardwareBuffer &)=delete
void * Lock(CPUAccessType type) const
Lock the buffer for CPU access. This call may fail if the buffer was not created with one the usages ...
std::optional< uint64_t > GetSystemUniqueID() const
Get the system wide unique ID of the hardware buffer if possible. This is only available on Android A...
int32_t value
const ProcTable & GetProcTable()
Definition: proc_table.cc:12
IMPELLER_ENUM_IS_MASK(MyMaskBits)
A descriptor use to specify hardware buffer allocations.
static HardwareBufferDescriptor MakeForSwapchainImage(const ISize &size)
Create a descriptor of the given size that is suitable for use as a swapchain image.
bool IsAllocatable() const
If hardware buffers can be created using this descriptor. Allocatable descriptors may still cause fai...
constexpr bool operator==(const HardwareBufferDescriptor &o) const =default