• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2007 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ANDROID_GRAPHIC_BUFFER_H
18 #define ANDROID_GRAPHIC_BUFFER_H
19 
20 #include <stdint.h>
21 #include <sys/types.h>
22 
23 #include <string>
24 #include <utility>
25 #include <vector>
26 
27 #include <android/hardware_buffer.h>
28 #include <ui/ANativeObjectBase.h>
29 #include <ui/GraphicBufferMapper.h>
30 #include <ui/PixelFormat.h>
31 #include <ui/Rect.h>
32 #include <utils/Flattenable.h>
33 #include <utils/RefBase.h>
34 
35 #include <nativebase/nativebase.h>
36 
37 #include <hardware/gralloc.h>
38 
39 namespace android {
40 
41 #ifndef LIBUI_IN_VNDK
42 class BufferHubBuffer;
43 #endif // LIBUI_IN_VNDK
44 
45 class GraphicBufferMapper;
46 
47 using GraphicBufferDeathCallback = std::function<void(void* /*context*/, uint64_t bufferId)>;
48 
49 // ===========================================================================
50 // GraphicBuffer
51 // ===========================================================================
52 
53 class GraphicBuffer
54     : public ANativeObjectBase<ANativeWindowBuffer, GraphicBuffer, RefBase>,
55       public Flattenable<GraphicBuffer>
56 {
57     friend class Flattenable<GraphicBuffer>;
58 public:
59 
60     enum {
61         USAGE_SW_READ_NEVER     = GRALLOC_USAGE_SW_READ_NEVER,
62         USAGE_SW_READ_RARELY    = GRALLOC_USAGE_SW_READ_RARELY,
63         USAGE_SW_READ_OFTEN     = GRALLOC_USAGE_SW_READ_OFTEN,
64         USAGE_SW_READ_MASK      = GRALLOC_USAGE_SW_READ_MASK,
65 
66         USAGE_SW_WRITE_NEVER    = GRALLOC_USAGE_SW_WRITE_NEVER,
67         USAGE_SW_WRITE_RARELY   = GRALLOC_USAGE_SW_WRITE_RARELY,
68         USAGE_SW_WRITE_OFTEN    = GRALLOC_USAGE_SW_WRITE_OFTEN,
69         USAGE_SW_WRITE_MASK     = GRALLOC_USAGE_SW_WRITE_MASK,
70 
71         USAGE_SOFTWARE_MASK     = USAGE_SW_READ_MASK|USAGE_SW_WRITE_MASK,
72 
73         USAGE_PROTECTED         = GRALLOC_USAGE_PROTECTED,
74 
75         USAGE_HW_TEXTURE        = GRALLOC_USAGE_HW_TEXTURE,
76         USAGE_HW_RENDER         = GRALLOC_USAGE_HW_RENDER,
77         USAGE_HW_2D             = GRALLOC_USAGE_HW_2D,
78         USAGE_HW_COMPOSER       = GRALLOC_USAGE_HW_COMPOSER,
79         USAGE_HW_VIDEO_ENCODER  = GRALLOC_USAGE_HW_VIDEO_ENCODER,
80         USAGE_HW_MASK           = GRALLOC_USAGE_HW_MASK,
81 
82         USAGE_CURSOR            = GRALLOC_USAGE_CURSOR,
83     };
84 
85     static sp<GraphicBuffer> from(ANativeWindowBuffer *);
86 
87     static GraphicBuffer* fromAHardwareBuffer(AHardwareBuffer*);
88     static GraphicBuffer const* fromAHardwareBuffer(AHardwareBuffer const*);
89     AHardwareBuffer* toAHardwareBuffer();
90     AHardwareBuffer const* toAHardwareBuffer() const;
91 
92     // Create a GraphicBuffer to be unflatten'ed into or be reallocated.
93     GraphicBuffer();
94 
95     // Create a GraphicBuffer by allocating and managing a buffer internally.
96     // This function is privileged.  See reallocate for details.
97     GraphicBuffer(uint32_t inWidth, uint32_t inHeight, PixelFormat inFormat,
98             uint32_t inLayerCount, uint64_t inUsage,
99             std::string requestorName = "<Unknown>");
100 
101     // Create a GraphicBuffer from an existing handle.
102     enum HandleWrapMethod : uint8_t {
103         // Wrap and use the handle directly.  It assumes the handle has been
104         // registered and never fails.  The handle must have a longer lifetime
105         // than this wrapping GraphicBuffer.
106         //
107         // This can be used when, for example, you want to wrap a handle that
108         // is already managed by another GraphicBuffer.
109         WRAP_HANDLE,
110 
111         // Take ownership of the handle and use it directly.  It assumes the
112         // handle has been registered and never fails.
113         //
114         // This can be used to manage an already registered handle with
115         // GraphicBuffer.
116         TAKE_HANDLE,
117 
118         // Take onwership of an unregistered handle and use it directly.  It
119         // can fail when the buffer does not register.  There is no ownership
120         // transfer on failures.
121         //
122         // This can be used to, for example, create a GraphicBuffer from a
123         // handle returned by Parcel::readNativeHandle.
124         TAKE_UNREGISTERED_HANDLE,
125 
126         // Make a clone of the handle and use the cloned handle.  It can fail
127         // when cloning fails or when the buffer does not register.  There is
128         // never ownership transfer.
129         //
130         // This can be used to create a GraphicBuffer from a handle that
131         // cannot be used directly, such as one from hidl_handle.
132         CLONE_HANDLE,
133     };
134     GraphicBuffer(const native_handle_t* inHandle, HandleWrapMethod method, uint32_t inWidth,
135                   uint32_t inHeight, PixelFormat inFormat, uint32_t inLayerCount, uint64_t inUsage,
136                   uint32_t inStride);
137 
138     // These functions are deprecated because they only take 32 bits of usage
GraphicBuffer(const native_handle_t * inHandle,HandleWrapMethod method,uint32_t inWidth,uint32_t inHeight,PixelFormat inFormat,uint32_t inLayerCount,uint32_t inUsage,uint32_t inStride)139     GraphicBuffer(const native_handle_t* inHandle, HandleWrapMethod method, uint32_t inWidth,
140                   uint32_t inHeight, PixelFormat inFormat, uint32_t inLayerCount, uint32_t inUsage,
141                   uint32_t inStride)
142           : GraphicBuffer(inHandle, method, inWidth, inHeight, inFormat, inLayerCount,
143                           static_cast<uint64_t>(inUsage), inStride) {}
144     GraphicBuffer(uint32_t inWidth, uint32_t inHeight, PixelFormat inFormat,
145             uint32_t inLayerCount, uint32_t inUsage, uint32_t inStride,
146             native_handle_t* inHandle, bool keepOwnership);
147     GraphicBuffer(uint32_t inWidth, uint32_t inHeight, PixelFormat inFormat,
148             uint32_t inUsage, std::string requestorName = "<Unknown>");
149 
150 #ifndef LIBUI_IN_VNDK
151     // Create a GraphicBuffer from an existing BufferHubBuffer.
152     GraphicBuffer(std::unique_ptr<BufferHubBuffer> buffer);
153 #endif // LIBUI_IN_VNDK
154 
155     // return status
156     status_t initCheck() const;
157 
getWidth()158     uint32_t getWidth() const           { return static_cast<uint32_t>(width); }
getHeight()159     uint32_t getHeight() const          { return static_cast<uint32_t>(height); }
getStride()160     uint32_t getStride() const          { return static_cast<uint32_t>(stride); }
getUsage()161     uint64_t getUsage() const           { return usage; }
getPixelFormat()162     PixelFormat getPixelFormat() const  { return format; }
getLayerCount()163     uint32_t getLayerCount() const      { return static_cast<uint32_t>(layerCount); }
getBounds()164     Rect getBounds() const              { return Rect(width, height); }
getId()165     uint64_t getId() const              { return mId; }
getBufferId()166     int32_t getBufferId() const { return mBufferId; }
167 
getGenerationNumber()168     uint32_t getGenerationNumber() const { return mGenerationNumber; }
setGenerationNumber(uint32_t generation)169     void setGenerationNumber(uint32_t generation) {
170         mGenerationNumber = generation;
171     }
172 
173     // This function is privileged.  It requires access to the allocator
174     // device or service, which usually involves adding suitable selinux
175     // rules.
176     status_t reallocate(uint32_t inWidth, uint32_t inHeight,
177             PixelFormat inFormat, uint32_t inLayerCount, uint64_t inUsage);
178 
179     bool needsReallocation(uint32_t inWidth, uint32_t inHeight,
180             PixelFormat inFormat, uint32_t inLayerCount, uint64_t inUsage);
181 
182     // For the following two lock functions, if bytesPerStride or bytesPerPixel
183     // are unknown or variable, -1 will be returned
184     status_t lock(uint32_t inUsage, void** vaddr, int32_t* outBytesPerPixel = nullptr,
185                   int32_t* outBytesPerStride = nullptr);
186     status_t lock(uint32_t inUsage, const Rect& rect, void** vaddr,
187                   int32_t* outBytesPerPixel = nullptr, int32_t* outBytesPerStride = nullptr);
188     // For HAL_PIXEL_FORMAT_YCbCr_420_888
189     status_t lockYCbCr(uint32_t inUsage, android_ycbcr *ycbcr);
190     status_t lockYCbCr(uint32_t inUsage, const Rect& rect,
191             android_ycbcr *ycbcr);
192     status_t unlock();
193     // For the following three lockAsync functions, if bytesPerStride or bytesPerPixel
194     // are unknown or variable, -1 will be returned
195     status_t lockAsync(uint32_t inUsage, void** vaddr, int fenceFd,
196                        int32_t* outBytesPerPixel = nullptr, int32_t* outBytesPerStride = nullptr);
197     status_t lockAsync(uint32_t inUsage, const Rect& rect, void** vaddr, int fenceFd,
198                        int32_t* outBytesPerPixel = nullptr, int32_t* outBytesPerStride = nullptr);
199     status_t lockAsync(uint64_t inProducerUsage, uint64_t inConsumerUsage, const Rect& rect,
200                        void** vaddr, int fenceFd, int32_t* outBytesPerPixel = nullptr,
201                        int32_t* outBytesPerStride = nullptr);
202     status_t lockAsyncYCbCr(uint32_t inUsage, android_ycbcr *ycbcr,
203             int fenceFd);
204     status_t lockAsyncYCbCr(uint32_t inUsage, const Rect& rect,
205             android_ycbcr *ycbcr, int fenceFd);
206     status_t unlockAsync(int *fenceFd);
207 
208     status_t isSupported(uint32_t inWidth, uint32_t inHeight, PixelFormat inFormat,
209                          uint32_t inLayerCount, uint64_t inUsage, bool* outSupported) const;
210 
211     ANativeWindowBuffer* getNativeBuffer() const;
212 
213     // for debugging
214     static void dumpAllocationsToSystemLog();
215 
216     // Flattenable protocol
217     size_t getFlattenedSize() const;
218     size_t getFdCount() const;
219     status_t flatten(void*& buffer, size_t& size, int*& fds, size_t& count) const;
220     status_t unflatten(void const*& buffer, size_t& size, int const*& fds, size_t& count);
221 
getBufferMapperVersion()222     GraphicBufferMapper::Version getBufferMapperVersion() const {
223         return mBufferMapper.getMapperVersion();
224     }
225 
226     void addDeathCallback(GraphicBufferDeathCallback deathCallback, void* context);
227 
228 #ifndef LIBUI_IN_VNDK
229     // Returns whether this GraphicBuffer is backed by BufferHubBuffer.
230     bool isBufferHubBuffer() const;
231 #endif // LIBUI_IN_VNDK
232 
233 private:
234     ~GraphicBuffer();
235 
236     enum {
237         ownNone   = 0,
238         ownHandle = 1,
239         ownData   = 2,
240     };
241 
getBufferMapper()242     inline const GraphicBufferMapper& getBufferMapper() const {
243         return mBufferMapper;
244     }
getBufferMapper()245     inline GraphicBufferMapper& getBufferMapper() {
246         return mBufferMapper;
247     }
248     uint8_t mOwner;
249 
250 private:
251     friend class Surface;
252     friend class BpSurface;
253     friend class BnSurface;
254     friend class LightRefBase<GraphicBuffer>;
255     GraphicBuffer(const GraphicBuffer& rhs);
256     GraphicBuffer& operator = (const GraphicBuffer& rhs);
257     const GraphicBuffer& operator = (const GraphicBuffer& rhs) const;
258 
259     status_t initWithSize(uint32_t inWidth, uint32_t inHeight,
260             PixelFormat inFormat, uint32_t inLayerCount,
261             uint64_t inUsage, std::string requestorName);
262 
263     status_t initWithHandle(const native_handle_t* inHandle, HandleWrapMethod method,
264                             uint32_t inWidth, uint32_t inHeight, PixelFormat inFormat,
265                             uint32_t inLayerCount, uint64_t inUsage, uint32_t inStride);
266 
267     void free_handle();
268 
269     GraphicBufferMapper& mBufferMapper;
270     ssize_t mInitCheck;
271 
272     // numbers of fds/ints in native_handle_t to flatten
273     uint32_t mTransportNumFds;
274     uint32_t mTransportNumInts;
275 
276     uint64_t mId;
277 
278     // System unique buffer ID. Note that this is different from mId, which is process unique. For
279     // GraphicBuffer backed by BufferHub, the mBufferId is a system unique identifier that stays the
280     // same cross process for the same chunck of underlying memory. Also note that this only applies
281     // to GraphicBuffers that are backed by BufferHub.
282     int32_t mBufferId = -1;
283 
284     // Stores the generation number of this buffer. If this number does not
285     // match the BufferQueue's internal generation number (set through
286     // IGBP::setGenerationNumber), attempts to attach the buffer will fail.
287     uint32_t mGenerationNumber;
288 
289     // Send a callback when a GraphicBuffer dies.
290     //
291     // This is used for BufferStateLayer caching. GraphicBuffers are refcounted per process. When
292     // A GraphicBuffer doesn't have any more sp<> in a process, it is destroyed. This causes
293     // problems when trying to implicitcly cache across process boundaries. Ideally, both sides
294     // of the cache would hold onto wp<> references. When an app dropped its sp<>, the GraphicBuffer
295     // would be destroyed. Unfortunately, when SurfaceFlinger has only a wp<> reference to the
296     // GraphicBuffer, it immediately goes out of scope in the SurfaceFlinger process. SurfaceFlinger
297     // must hold onto a sp<> to the buffer. When the GraphicBuffer goes out of scope in the app's
298     // process, the client side cache will get this callback. It erases the buffer from its cache
299     // and informs SurfaceFlinger that it should drop its strong pointer reference to the buffer.
300     std::vector<std::pair<GraphicBufferDeathCallback, void* /*mDeathCallbackContext*/>>
301             mDeathCallbacks;
302 
303 #ifndef LIBUI_IN_VNDK
304     // Flatten this GraphicBuffer object if backed by BufferHubBuffer.
305     status_t flattenBufferHubBuffer(void*& buffer, size_t& size) const;
306 
307     // Unflatten into BufferHubBuffer backed GraphicBuffer.
308     // Unflatten will fail if the original GraphicBuffer object is destructed. For instance, a
309     // GraphicBuffer backed by BufferHubBuffer_1 flatten in process/thread A, transport the token
310     // to process/thread B through a socket, BufferHubBuffer_1 dies and bufferhub invalidated the
311     // token. Race condition occurs between the invalidation of the token in bufferhub process and
312     // process/thread B trying to unflatten and import the buffer with that token.
313     status_t unflattenBufferHubBuffer(void const*& buffer, size_t& size);
314 
315     // Stores a BufferHubBuffer that handles buffer signaling, identification.
316     std::unique_ptr<BufferHubBuffer> mBufferHubBuffer;
317 #endif // LIBUI_IN_VNDK
318 };
319 
320 }; // namespace android
321 
322 #endif // ANDROID_GRAPHIC_BUFFER_H
323