2 // Copyright (c) 2017 Intel Corporation
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
8 // http://www.apache.org/licenses/LICENSE-2.0
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.
17 #include "compositorthread.h"
21 #include "nativegpuresource.h"
22 #include "overlaylayer.h"
24 #include "displayplanemanager.h"
25 #include "nativesurface.h"
27 namespace hwcomposer {
29 CompositorThread::CompositorThread() : HWCThread(-8, "CompositorThread") {
30 if (!cevent_.Initialize())
33 fd_chandler_.AddFd(cevent_.get_fd());
36 CompositorThread::~CompositorThread() {
39 void CompositorThread::Initialize(DisplayPlaneManager *plane_manager) {
40 gpu_resource_handler_.reset(CreateNativeGpuResourceHandler());
41 plane_manager_ = plane_manager;
43 ETRACE("Failed to initalize CompositorThread. %s", PRINTERROR());
47 void CompositorThread::SetExplicitSyncSupport(bool disable_explicit_sync) {
48 disable_explicit_sync_ = disable_explicit_sync;
51 void CompositorThread::EnsureTasksAreDone() {
56 void CompositorThread::FreeResources(bool all_resources) {
57 release_all_resources_ = all_resources;
59 tasks_ |= kReleaseResources;
64 void CompositorThread::Wait() {
65 if (fd_chandler_.Poll(-1) <= 0) {
66 ETRACE("Poll Failed in DisplayManager %s", PRINTERROR());
70 if (fd_chandler_.IsReady(cevent_.get_fd())) {
71 // If eventfd_ is ready, we need to wait on it (using read()) to clean
72 // the flag that says it is ready.
77 void CompositorThread::Draw(std::vector<DrawState> &states,
78 const std::vector<OverlayLayer> &layers) {
80 std::vector<OverlayBuffer *>().swap(buffers_);
81 for (auto &layer : layers) {
82 buffers_.emplace_back(layer.GetBuffer());
92 void CompositorThread::ExitThread() {
93 release_all_resources_ = true;
96 renderer_.reset(nullptr);
97 std::vector<DrawState>().swap(states_);
98 std::vector<OverlayBuffer *>().swap(buffers_);
101 void CompositorThread::ReleaseGpuResources() {
102 gpu_resource_handler_->ReleaseGPUResources();
105 void CompositorThread::HandleRoutine() {
106 if (tasks_ & kRender) {
111 if (tasks_ & kReleaseResources) {
112 HandleReleaseRequest();
116 void CompositorThread::HandleReleaseRequest() {
117 ScopedSpinLock lock(tasks_lock_);
118 tasks_ &= ~kReleaseResources;
123 if (!plane_manager_->HasSurfaces())
127 renderer_.reset(CreateRenderer());
128 if (!renderer_->Init()) {
129 ETRACE("Failed to initialize OpenGL compositor %s", PRINTERROR());
130 renderer_.reset(nullptr);
135 if (release_all_resources_) {
136 plane_manager_->ReleaseAllOffScreenTargets();
138 plane_manager_->ReleaseFreeOffScreenTargets();
142 void CompositorThread::HandleDrawRequest() {
145 tasks_lock_.unlock();
148 renderer_.reset(CreateRenderer());
149 if (!renderer_->Init()) {
150 ETRACE("Failed to initialize OpenGL compositor %s", PRINTERROR());
151 renderer_.reset(nullptr);
156 renderer_->SetExplicitSyncSupport(disable_explicit_sync_);
158 if (!gpu_resource_handler_->PrepareResources(buffers_)) {
160 "Failed to prepare GPU resources for compositing the frame, "
163 ReleaseGpuResources();
167 size_t size = states_.size();
168 for (size_t i = 0; i < size; i++) {
169 DrawState &draw_state = states_.at(i);
170 for (RenderState &render_state : draw_state.states_) {
171 std::vector<RenderState::LayerState> &layer_state =
172 render_state.layer_state_;
174 for (RenderState::LayerState &temp : layer_state) {
176 gpu_resource_handler_->GetResourceHandle(temp.layer_index_);
180 const std::vector<int32_t> &fences = draw_state.acquire_fences_;
181 for (int32_t fence : fences) {
182 renderer_->InsertFence(fence);
185 if (!renderer_->Draw(draw_state.states_, draw_state.surface_,
186 draw_state.clear_surface_)) {
188 "Failed to prepare GPU resources for compositing the frame, "
194 if (draw_state.destroy_surface_) {
195 draw_state.retire_fence_ =
196 draw_state.surface_->GetLayer()->ReleaseAcquireFence();
197 delete draw_state.surface_;
201 if (disable_explicit_sync_)
202 renderer_->InsertFence(-1);
205 } // namespace hwcomposer