1#ifndef ANDROID_DVR_NATIVE_BUFFER_H_
2#define ANDROID_DVR_NATIVE_BUFFER_H_
3
4#include <EGL/egl.h>
5#include <EGL/eglext.h>
6#include <log/log.h>
7#include <ui/ANativeObjectBase.h>
8#include <utils/RefBase.h>
9#include <nativebase/nativebase.h>
10
11#include <private/dvr/buffer_hub_client.h>
12
13namespace android {
14namespace dvr {
15
16// ANativeWindowBuffer is the abstraction Android HALs and frameworks use to
17// pass around hardware graphics buffers. The following classes implement this
18// abstraction with different DVR backing buffers, all of which provide
19// different semantics on top of ion/gralloc buffers.
20
21// An implementation of ANativeWindowBuffer backed by an IonBuffer.
22class NativeBuffer
23    : public android::ANativeObjectBase<ANativeWindowBuffer, NativeBuffer,
24                                        android::LightRefBase<NativeBuffer>> {
25 public:
26  static constexpr int kEmptyFence = -1;
27
28  explicit NativeBuffer(const std::shared_ptr<IonBuffer>& buffer)
29      : BASE(), buffer_(buffer), fence_(kEmptyFence) {
30    ANativeWindowBuffer::width = buffer->width();
31    ANativeWindowBuffer::height = buffer->height();
32    ANativeWindowBuffer::stride = buffer->stride();
33    ANativeWindowBuffer::format = buffer->format();
34    ANativeWindowBuffer::usage = buffer->usage();
35    handle = buffer_->handle();
36  }
37
38  virtual ~NativeBuffer() {}
39
40  std::shared_ptr<IonBuffer> buffer() { return buffer_; }
41  int fence() const { return fence_.Get(); }
42
43  void SetFence(int fence) { fence_.Reset(fence); }
44
45 private:
46  friend class android::LightRefBase<NativeBuffer>;
47
48  std::shared_ptr<IonBuffer> buffer_;
49  pdx::LocalHandle fence_;
50
51  NativeBuffer(const NativeBuffer&) = delete;
52  void operator=(NativeBuffer&) = delete;
53};
54
55class NativeBufferProducer : public android::ANativeObjectBase<
56                                 ANativeWindowBuffer, NativeBufferProducer,
57                                 android::LightRefBase<NativeBufferProducer>> {
58 public:
59  static constexpr int kEmptyFence = -1;
60
61  NativeBufferProducer(const std::shared_ptr<BufferProducer>& buffer,
62                       EGLDisplay display, uint32_t surface_buffer_index)
63      : BASE(),
64        buffer_(buffer),
65        surface_buffer_index_(surface_buffer_index),
66        display_(display) {
67    ANativeWindowBuffer::width = buffer_->width();
68    ANativeWindowBuffer::height = buffer_->height();
69    ANativeWindowBuffer::stride = buffer_->stride();
70    ANativeWindowBuffer::format = buffer_->format();
71    ANativeWindowBuffer::usage = buffer_->usage();
72    ANativeWindowBuffer::handle = buffer_->native_handle();
73    if (display_) {
74      image_khr_ =
75          eglCreateImageKHR(display_, EGL_NO_CONTEXT, EGL_NATIVE_BUFFER_ANDROID,
76                            static_cast<ANativeWindowBuffer*>(this), nullptr);
77    } else {
78      image_khr_ = EGL_NO_IMAGE_KHR;
79    }
80  }
81
82  explicit NativeBufferProducer(const std::shared_ptr<BufferProducer>& buffer)
83      : NativeBufferProducer(buffer, nullptr, 0) {}
84
85  virtual ~NativeBufferProducer() {
86    if (image_khr_ != EGL_NO_IMAGE_KHR)
87      eglDestroyImageKHR(display_, image_khr_);
88  }
89
90  EGLImageKHR image_khr() const { return image_khr_; }
91  std::shared_ptr<BufferProducer> buffer() const { return buffer_; }
92  int release_fence() const { return release_fence_.Get(); }
93  uint32_t surface_buffer_index() const { return surface_buffer_index_; }
94
95  // Return the release fence, passing ownership to the caller.
96  pdx::LocalHandle ClaimReleaseFence() { return std::move(release_fence_); }
97
98  // Post the buffer consumer, closing the acquire and release fences.
99  int Post(int acquire_fence, uint64_t sequence) {
100    release_fence_.Close();
101    return buffer_->Post(pdx::LocalHandle(acquire_fence), sequence);
102  }
103
104  // Gain the buffer producer, closing the previous release fence if valid.
105  int Gain() { return buffer_->Gain(&release_fence_); }
106
107  // Asynchronously gain the buffer, closing the previous release fence.
108  int GainAsync() {
109    release_fence_.Close();
110    return buffer_->GainAsync();
111  }
112
113 private:
114  friend class android::LightRefBase<NativeBufferProducer>;
115
116  std::shared_ptr<BufferProducer> buffer_;
117  pdx::LocalHandle release_fence_;
118  EGLImageKHR image_khr_;
119  uint32_t surface_buffer_index_;
120  EGLDisplay display_;
121
122  NativeBufferProducer(const NativeBufferProducer&) = delete;
123  void operator=(NativeBufferProducer&) = delete;
124};
125
126// NativeBufferConsumer is an implementation of ANativeWindowBuffer backed by a
127// BufferConsumer.
128class NativeBufferConsumer : public android::ANativeObjectBase<
129                                 ANativeWindowBuffer, NativeBufferConsumer,
130                                 android::LightRefBase<NativeBufferConsumer>> {
131 public:
132  static constexpr int kEmptyFence = -1;
133
134  explicit NativeBufferConsumer(const std::shared_ptr<BufferConsumer>& buffer)
135      : BASE(), buffer_(buffer), acquire_fence_(kEmptyFence), sequence_(0) {
136    ANativeWindowBuffer::width = buffer_->width();
137    ANativeWindowBuffer::height = buffer_->height();
138    ANativeWindowBuffer::stride = buffer_->stride();
139    ANativeWindowBuffer::format = buffer_->format();
140    ANativeWindowBuffer::usage = buffer_->usage();
141    handle = buffer_->native_handle();
142  }
143
144  virtual ~NativeBufferConsumer() {}
145
146  std::shared_ptr<BufferConsumer> buffer() const { return buffer_; }
147  int acquire_fence() const { return acquire_fence_.Get(); }
148  uint64_t sequence() const { return sequence_; }
149
150  // Return the acquire fence, passing ownership to the caller.
151  pdx::LocalHandle ClaimAcquireFence() { return std::move(acquire_fence_); }
152
153  // Acquire the underlying buffer consumer, closing the previous acquire fence
154  // if valid.
155  int Acquire() { return buffer_->Acquire(&acquire_fence_, &sequence_); }
156
157  // Release the buffer consumer, closing the acquire and release fences if
158  // valid.
159  int Release(int release_fence) {
160    acquire_fence_.Close();
161    sequence_ = 0;
162    return buffer_->Release(pdx::LocalHandle(release_fence));
163  }
164
165 private:
166  friend class android::LightRefBase<NativeBufferConsumer>;
167
168  std::shared_ptr<BufferConsumer> buffer_;
169  pdx::LocalHandle acquire_fence_;
170  uint64_t sequence_;
171
172  NativeBufferConsumer(const NativeBufferConsumer&) = delete;
173  void operator=(NativeBufferConsumer&) = delete;
174};
175
176}  // namespace dvr
177}  // namespace android
178
179#endif  // ANDROID_DVR_NATIVE_BUFFER_H_
180