• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2021 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "avbuffer_queue_consumer_impl.h"
17 #include "avbuffer_queue_producer_impl.h"
18 #include "common/log.h"
19 
20 
21 namespace OHOS {
22 namespace Media {
23 
AVBufferQueueSurfaceWrapper(sptr<Surface> & surface,const std::string & name,uint8_t wrapperType)24 AVBufferQueueSurfaceWrapper::AVBufferQueueSurfaceWrapper(
25     sptr<Surface> &surface, const std::string &name, uint8_t wrapperType)
26     : AVBufferQueueImpl(surface->GetQueueSize(), MemoryType::UNKNOWN_MEMORY, name),
27       surface_(surface), wrapperType_(wrapperType)
28 {
29     for (uint32_t i = 0; i < surface->GetQueueSize(); i++) {
30         auto buffer = AVBuffer::CreateAVBuffer();
31         cachedBufferMap_[buffer->GetUniqueId()] = buffer;
32         freeBufferList_.emplace_back(buffer->GetUniqueId());
33     }
34 }
35 
GetProducer()36 sptr<AVBufferQueueProducer> AVBufferQueueSurfaceWrapper::GetProducer()
37 {
38     return AVBufferQueueImpl::GetProducer();
39 }
40 
GetConsumer()41 sptr<AVBufferQueueConsumer> AVBufferQueueSurfaceWrapper::GetConsumer()
42 {
43     if (wrapperType_ == PRODUCER_WRAPPER) {
44         return nullptr;
45     }
46     return AVBufferQueueImpl::GetConsumer();
47 }
48 
GetSurfaceAsProducer()49 sptr<Surface> AVBufferQueueSurfaceWrapper::GetSurfaceAsProducer()
50 {
51     if (wrapperType_ == PRODUCER_WRAPPER || wrapperType_ == BOTH_WRAPPER) {
52         return nullptr;
53     }
54     return surface_;
55 }
56 
GetSurfaceAsConsumer()57 sptr<Surface> AVBufferQueueSurfaceWrapper::GetSurfaceAsConsumer()
58 {
59     if (wrapperType_ == CONSUMER_WRAPPER || wrapperType_ == BOTH_WRAPPER) {
60         return nullptr;
61     }
62     return surface_;
63 }
64 
GetQueueSize()65 uint32_t AVBufferQueueSurfaceWrapper::GetQueueSize()
66 {
67     return surface_->GetQueueSize();
68 }
69 
SetQueueSize(uint32_t size)70 Status AVBufferQueueSurfaceWrapper::SetQueueSize(uint32_t size)
71 {
72     NZERO_RETURN_V(surface_->SetQueueSize(size), Status::ERROR_SURFACE_INNER);
73 
74     std::lock_guard<std::mutex> lockGuard(queueMutex_);
75 
76     auto curSize = cachedBufferMap_.size();
77     if (size > curSize) {
78         for (auto i = curSize; i < size; ++i) {
79             auto buffer = AVBuffer::CreateAVBuffer();
80             cachedBufferMap_[buffer->GetUniqueId()] = buffer;
81             freeBufferList_.emplace_back(buffer->GetUniqueId());
82         }
83     }
84 
85     return Status::OK;
86 }
87 
BindSurface(std::shared_ptr<AVBuffer> & buffer,sptr<SurfaceBuffer> & surfaceBuffer,int32_t fence)88 Status AVBufferQueueSurfaceWrapper::BindSurface(
89     std::shared_ptr<AVBuffer>& buffer, sptr<SurfaceBuffer>& surfaceBuffer, int32_t fence)
90 {
91     std::lock_guard<std::mutex> lockGuard(queueMutex_);
92     if (freeBufferList_.empty()) {
93         MEDIA_LOG_W("cannot find free buffer, alloc new one");
94         buffer = AVBuffer::CreateAVBuffer();
95         cachedBufferMap_[buffer->GetUniqueId()] = buffer;
96     } else {
97         buffer = cachedBufferMap_[freeBufferList_.front()];
98         freeBufferList_.pop_front();
99     }
100     return Status::OK;
101 }
102 
UnbindSurface(uint64_t uniqueId,sptr<SurfaceBuffer> & surfaceBuffer,int32_t & fence,BufferFlushConfig & config)103 Status AVBufferQueueSurfaceWrapper::UnbindSurface(uint64_t uniqueId, sptr<SurfaceBuffer>& surfaceBuffer, int32_t& fence,
104                                                   BufferFlushConfig& config)
105 {
106     std::lock_guard<std::mutex> lockGuard(queueMutex_);
107     FALSE_RETURN_V(cachedBufferMap_.find(uniqueId) != cachedBufferMap_.end(), Status::ERROR_INVALID_BUFFER_ID);
108     freeBufferList_.emplace_back(uniqueId);
109 
110     return Status::OK;
111 }
112 
RequestBuffer(std::shared_ptr<AVBuffer> & buffer,const AVBufferConfig & config,int32_t timeoutMs)113 Status AVBufferQueueSurfaceWrapper::RequestBuffer(
114     std::shared_ptr<AVBuffer>& buffer, const AVBufferConfig& config, int32_t timeoutMs)
115 {
116     sptr<SurfaceBuffer> surfaceBuffer = nullptr;
117     int32_t fence;
118     FALSE_RETURN_V(config.surfaceBufferConfig != nullptr, Status::ERROR_INVALID_PARAMETER);
119     BufferRequestConfig surfaceBufferConfig = *(config.surfaceBufferConfig);
120     NZERO_RETURN_V(surface_->RequestBuffer(surfaceBuffer, fence, surfaceBufferConfig),
121                    Status::ERROR_SURFACE_INNER);
122 
123     return BindSurface(buffer, surfaceBuffer, fence);
124 }
125 
CancelBuffer(uint64_t uniqueId)126 Status AVBufferQueueSurfaceWrapper::CancelBuffer(uint64_t uniqueId)
127 {
128     sptr<SurfaceBuffer> surfaceBuffer = nullptr;
129     int32_t fence;
130     BufferFlushConfig config;
131     return UnbindSurface(uniqueId, surfaceBuffer, fence, config);
132 }
133 
PushBuffer(uint64_t uniqueId,bool available)134 Status AVBufferQueueSurfaceWrapper::PushBuffer(uint64_t uniqueId, bool available)
135 {
136     if (brokerListener_ != nullptr) {
137         std::lock_guard<std::mutex> lockGuard(brokerListenerMutex_);
138         if (brokerListener_ != nullptr) {
139             brokerListener_->OnBufferFilled(cachedBufferMap_[uniqueId]);
140             return Status::OK;
141         }
142     }
143 
144     return ReturnBuffer(uniqueId, available);
145 }
146 
PushBuffer(const std::shared_ptr<AVBuffer> & buffer,bool available)147 Status AVBufferQueueSurfaceWrapper::PushBuffer(const std::shared_ptr<AVBuffer>& buffer, bool available)
148 {
149     FALSE_RETURN_V(buffer != nullptr, Status::ERROR_NULL_POINT_BUFFER);
150 
151     return PushBuffer(buffer->GetUniqueId(), available);
152 }
153 
ReturnBuffer(uint64_t uniqueId,bool available)154 Status AVBufferQueueSurfaceWrapper::ReturnBuffer(uint64_t uniqueId, bool available)
155 {
156     if (!available) {
157         return CancelBuffer(uniqueId);
158     }
159 
160     int32_t fence;
161     sptr<SurfaceBuffer> surfaceBuffer = nullptr;
162     BufferFlushConfig config;
163     NOK_RETURN(UnbindSurface(uniqueId, surfaceBuffer, fence, config));
164 
165     NZERO_RETURN_V(surface_->FlushBuffer(surfaceBuffer, fence, config), Status::ERROR_SURFACE_INNER);
166 
167     return Status::OK;
168 }
169 
ReturnBuffer(const std::shared_ptr<AVBuffer> & buffer,bool available)170 Status AVBufferQueueSurfaceWrapper::ReturnBuffer(const std::shared_ptr<AVBuffer>& buffer, bool available)
171 {
172     FALSE_RETURN_V(buffer != nullptr, Status::ERROR_NULL_POINT_BUFFER);
173     return ReturnBuffer(buffer->GetUniqueId(), available);
174 }
175 
AttachBuffer(std::shared_ptr<AVBuffer> & buffer,bool isFilled)176 Status AVBufferQueueSurfaceWrapper::AttachBuffer(std::shared_ptr<AVBuffer>& buffer, bool isFilled)
177 {
178     FALSE_RETURN_V(buffer != nullptr, Status::ERROR_NULL_POINT_BUFFER);
179     FALSE_RETURN_V(!isFilled, Status::ERROR_INVALID_PARAMETER);
180     return Status::OK;
181 }
182 
DetachBuffer(uint64_t uniqueId)183 Status AVBufferQueueSurfaceWrapper::DetachBuffer(uint64_t uniqueId)
184 {
185     sptr<SurfaceBuffer> surfaceBuffer = nullptr;
186     int32_t fence;
187     BufferFlushConfig config;
188     NOK_RETURN(UnbindSurface(uniqueId, surfaceBuffer, fence, config));
189 
190     NZERO_RETURN_V(surface_->DetachBuffer(surfaceBuffer), Status::ERROR_SURFACE_INNER);
191 
192     return Status::OK;
193 }
194 
DetachBuffer(const std::shared_ptr<AVBuffer> & buffer)195 Status AVBufferQueueSurfaceWrapper::DetachBuffer(const std::shared_ptr<AVBuffer>& buffer)
196 {
197     FALSE_RETURN_V(buffer != nullptr, Status::ERROR_NULL_POINT_BUFFER);
198 
199     NOK_RETURN(DetachBuffer(buffer->GetUniqueId()));
200 
201     return Status::OK;
202 }
203 
AcquireBuffer(std::shared_ptr<AVBuffer> & buffer)204 Status AVBufferQueueSurfaceWrapper::AcquireBuffer(std::shared_ptr<AVBuffer>& buffer)
205 {
206     sptr<SurfaceBuffer> surfaceBuffer = nullptr;
207     int32_t fence;
208     int64_t timestamp;
209     Rect range;
210     NZERO_RETURN_V(surface_->AcquireBuffer(surfaceBuffer, fence, timestamp, range),
211                    Status::ERROR_SURFACE_INNER);
212 
213     NOK_RETURN(BindSurface(buffer, surfaceBuffer, fence));
214 
215     return Status::OK;
216 }
217 
ReleaseBuffer(uint64_t uniqueId)218 Status AVBufferQueueSurfaceWrapper::ReleaseBuffer(uint64_t uniqueId)
219 {
220     sptr<SurfaceBuffer> surfaceBuffer = nullptr;
221     int32_t fence;
222     BufferFlushConfig config;
223     NOK_RETURN(UnbindSurface(uniqueId, surfaceBuffer, fence, config));
224     NZERO_RETURN_V(surface_->ReleaseBuffer(surfaceBuffer, fence), Status::ERROR_SURFACE_INNER);
225     return Status::OK;
226 }
227 
ReleaseBuffer(const std::shared_ptr<AVBuffer> & buffer)228 Status AVBufferQueueSurfaceWrapper::ReleaseBuffer(const std::shared_ptr<AVBuffer>& buffer)
229 {
230     FALSE_RETURN_V(buffer != nullptr, Status::ERROR_NULL_POINT_BUFFER);
231     return ReleaseBuffer(buffer->GetUniqueId());
232 }
233 
SetBrokerListener(sptr<IBrokerListener> & listener)234 Status AVBufferQueueSurfaceWrapper::SetBrokerListener(sptr<IBrokerListener>& listener)
235 {
236     std::lock_guard<std::mutex> lockGuard(producerListenerMutex_);
237     brokerListener_ = listener;
238     return Status::OK;
239 }
240 
SetProducerListener(sptr<IProducerListener> & listener)241 Status AVBufferQueueSurfaceWrapper::SetProducerListener(sptr<IProducerListener>& listener)
242 {
243     std::lock_guard<std::mutex> lockGuard(producerListenerMutex_);
244     producerListener_ = listener;
245     return Status::OK;
246 }
247 
248 class SurfaceConsumerListener : public IBufferConsumerListener {
249 public:
SurfaceConsumerListener(std::function<void ()> releaseBufferFunc)250     explicit SurfaceConsumerListener(std::function<void()> releaseBufferFunc)
251         : onReleaseBufferFunc_(std::move(releaseBufferFunc)) {}
252 
OnBufferAvailable()253     void OnBufferAvailable() override { onReleaseBufferFunc_(); }
254 
255 private:
256     std::function<void(void)> onReleaseBufferFunc_;
257 };
258 
SetConsumerListener(sptr<IConsumerListener> & listener)259 Status AVBufferQueueSurfaceWrapper::SetConsumerListener(sptr<IConsumerListener>& listener)
260 {
261     auto releaseBufferFunc = [this]()->void {
262         std::lock_guard<std::mutex> lockGuard(consumerListenerMutex_);
263         if (consumerListener_ != nullptr) {
264             consumerListener_->OnBufferAvailable();
265         }
266     };
267 
268     std::lock_guard<std::mutex> lockGuard(consumerListenerMutex_);
269     if (listener == nullptr) {
270         surfaceConsumerListener_ = nullptr;
271         surface_->RegisterConsumerListener(nullptr);
272     } else {
273         surfaceConsumerListener_ = new SurfaceConsumerListener(releaseBufferFunc);
274         surface_->RegisterConsumerListener(surfaceConsumerListener_);
275     }
276 
277     consumerListener_ = listener;
278 
279     return Status::OK;
280 }
281 
282 }
283 }