blob: 66197be44ad29c80c9172e0383ef5392d6047434 [file] [log] [blame]
Vishnu Nairdc4d31b2022-11-17 03:20:58 +00001/*
2 * Copyright 2022 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#define ATRACE_TAG ATRACE_TAG_GRAPHICS
18
19#undef LOG_TAG
20#define LOG_TAG "LayerLifecycleManager"
21
22#include "LayerLifecycleManager.h"
23#include "Layer.h" // temporarily needed for LayerHandle
24#include "LayerHandle.h"
Vishnu Nair80a5a702023-02-11 01:21:51 +000025#include "LayerLog.h"
Vishnu Nairdc4d31b2022-11-17 03:20:58 +000026#include "SwapErase.h"
27
28namespace android::surfaceflinger::frontend {
29
30using namespace ftl::flag_operators;
31
32void LayerLifecycleManager::addLayers(std::vector<std::unique_ptr<RequestedLayerState>> newLayers) {
33 if (newLayers.empty()) {
34 return;
35 }
36
37 mGlobalChanges |= RequestedLayerState::Changes::Hierarchy;
38 for (auto& newLayer : newLayers) {
39 RequestedLayerState& layer = *newLayer.get();
Vishnu Nair80a5a702023-02-11 01:21:51 +000040 LLOGV(layer.id, "%s layer %s", __func__, layer.getDebugStringShort().c_str());
Vishnu Nairdc4d31b2022-11-17 03:20:58 +000041 auto [it, inserted] = mIdToLayer.try_emplace(layer.id, References{.owner = layer});
42 if (!inserted) {
43 LOG_ALWAYS_FATAL("Duplicate layer id %d found. Existing layer: %s", layer.id,
44 it->second.owner.getDebugString().c_str());
45 }
46
Vishnu Nair04f89692022-11-16 23:21:05 +000047 layer.parentId = linkLayer(layer.parentId, layer.id);
48 layer.relativeParentId = linkLayer(layer.relativeParentId, layer.id);
Vishnu Naira9c43762023-01-27 19:10:25 +000049 if (layer.layerStackToMirror != ui::INVALID_LAYER_STACK) {
50 // if this layer is mirroring a display, then walk though all the existing root layers
51 // for the layer stack and add them as children to be mirrored.
52 mDisplayMirroringLayers.emplace_back(layer.id);
53 for (auto& rootLayer : mLayers) {
54 if (rootLayer->isRoot() && rootLayer->layerStack == layer.layerStackToMirror) {
55 layer.mirrorIds.emplace_back(rootLayer->id);
56 linkLayer(rootLayer->id, layer.id);
57 }
58 }
59 } else {
60 // Check if we are mirroring a single layer, and if so add it to the list of children
61 // to be mirrored.
62 layer.layerIdToMirror = linkLayer(layer.layerIdToMirror, layer.id);
63 if (layer.layerIdToMirror != UNASSIGNED_LAYER_ID) {
64 layer.mirrorIds.emplace_back(layer.layerIdToMirror);
65 }
66 }
Vishnu Nair04f89692022-11-16 23:21:05 +000067 layer.touchCropId = linkLayer(layer.touchCropId, layer.id);
Vishnu Naira9c43762023-01-27 19:10:25 +000068 if (layer.isRoot()) {
69 updateDisplayMirrorLayers(layer);
70 }
Vishnu Nairdc4d31b2022-11-17 03:20:58 +000071 mLayers.emplace_back(std::move(newLayer));
72 }
73}
74
75void LayerLifecycleManager::onHandlesDestroyed(const std::vector<uint32_t>& destroyedHandles) {
76 std::vector<uint32_t> layersToBeDestroyed;
77 for (const auto& layerId : destroyedHandles) {
78 auto it = mIdToLayer.find(layerId);
79 if (it == mIdToLayer.end()) {
80 LOG_ALWAYS_FATAL("%s Layerid not found %d", __func__, layerId);
81 continue;
82 }
83 RequestedLayerState& layer = it->second.owner;
84 layer.handleAlive = false;
85 if (!layer.canBeDestroyed()) {
86 continue;
87 }
88 layer.changes |= RequestedLayerState::Changes::Destroyed;
89 layersToBeDestroyed.emplace_back(layerId);
90 }
91
92 if (layersToBeDestroyed.empty()) {
93 return;
94 }
95
96 mGlobalChanges |= RequestedLayerState::Changes::Hierarchy;
97 for (size_t i = 0; i < layersToBeDestroyed.size(); i++) {
98 uint32_t layerId = layersToBeDestroyed[i];
99 auto it = mIdToLayer.find(layerId);
100 if (it == mIdToLayer.end()) {
101 LOG_ALWAYS_FATAL("%s Layer with id %d not found", __func__, layerId);
102 continue;
103 }
104
105 RequestedLayerState& layer = it->second.owner;
106
Vishnu Nair04f89692022-11-16 23:21:05 +0000107 layer.parentId = unlinkLayer(layer.parentId, layer.id);
108 layer.relativeParentId = unlinkLayer(layer.relativeParentId, layer.id);
Vishnu Naira9c43762023-01-27 19:10:25 +0000109 if (layer.layerStackToMirror != ui::INVALID_LAYER_STACK) {
110 layer.mirrorIds = unlinkLayers(layer.mirrorIds, layer.id);
111 swapErase(mDisplayMirroringLayers, layer.id);
112 } else {
113 layer.layerIdToMirror = unlinkLayer(layer.layerIdToMirror, layer.id);
114 layer.mirrorIds.clear();
115 }
116
Vishnu Nair04f89692022-11-16 23:21:05 +0000117 layer.touchCropId = unlinkLayer(layer.touchCropId, layer.id);
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000118
119 auto& references = it->second.references;
120 for (uint32_t linkedLayerId : references) {
121 RequestedLayerState* linkedLayer = getLayerFromId(linkedLayerId);
122 if (!linkedLayer) {
123 LOG_ALWAYS_FATAL("%s Layerid reference %d not found for %d", __func__,
124 linkedLayerId, layer.id);
125 continue;
126 };
127 if (linkedLayer->parentId == layer.id) {
128 linkedLayer->parentId = UNASSIGNED_LAYER_ID;
129 if (linkedLayer->canBeDestroyed()) {
130 linkedLayer->changes |= RequestedLayerState::Changes::Destroyed;
131 layersToBeDestroyed.emplace_back(linkedLayer->id);
132 }
133 }
134 if (linkedLayer->relativeParentId == layer.id) {
135 linkedLayer->relativeParentId = UNASSIGNED_LAYER_ID;
136 }
Vishnu Naira9c43762023-01-27 19:10:25 +0000137 if (swapErase(linkedLayer->mirrorIds, layer.id)) {
138 linkedLayer->changes |= RequestedLayerState::Changes::Mirror;
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000139 }
140 if (linkedLayer->touchCropId == layer.id) {
141 linkedLayer->touchCropId = UNASSIGNED_LAYER_ID;
142 }
143 }
144 mIdToLayer.erase(it);
145 }
146
147 auto it = mLayers.begin();
148 while (it != mLayers.end()) {
149 RequestedLayerState* layer = it->get();
150 if (layer->changes.test(RequestedLayerState::Changes::Destroyed)) {
Vishnu Nair80a5a702023-02-11 01:21:51 +0000151 LLOGV(layer->id, "destroyed layer %s", layer->getDebugStringShort().c_str());
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000152 std::iter_swap(it, mLayers.end() - 1);
153 mDestroyedLayers.emplace_back(std::move(mLayers.back()));
Vishnu Nairaa548fd2022-11-23 18:50:09 +0000154 if (it == mLayers.end() - 1) {
155 it = mLayers.erase(mLayers.end() - 1);
156 } else {
157 mLayers.erase(mLayers.end() - 1);
158 }
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000159 } else {
160 it++;
161 }
162 }
163}
164
165void LayerLifecycleManager::applyTransactions(const std::vector<TransactionState>& transactions) {
166 for (const auto& transaction : transactions) {
167 for (const auto& resolvedComposerState : transaction.states) {
168 const auto& clientState = resolvedComposerState.state;
169 uint32_t layerId = LayerHandle::getLayerId(clientState.surface);
170 if (layerId == UNASSIGNED_LAYER_ID) {
171 ALOGW("%s Handle %p is not valid", __func__, clientState.surface.get());
172 continue;
173 }
174
175 RequestedLayerState* layer = getLayerFromId(layerId);
176 if (layer == nullptr) {
177 LOG_ALWAYS_FATAL("%s Layer with handle %p (layerid=%d) not found", __func__,
178 clientState.surface.get(), layerId);
179 continue;
180 }
181
182 if (!layer->handleAlive) {
183 LOG_ALWAYS_FATAL("%s Layer's handle %p (layerid=%d) is not alive. Possible out of "
184 "order LayerLifecycleManager updates",
185 __func__, clientState.surface.get(), layerId);
186 continue;
187 }
188
189 uint32_t oldParentId = layer->parentId;
190 uint32_t oldRelativeParentId = layer->relativeParentId;
191 uint32_t oldTouchCropId = layer->touchCropId;
192 layer->merge(resolvedComposerState);
193
194 if (layer->what & layer_state_t::eBackgroundColorChanged) {
195 if (layer->bgColorLayerId == UNASSIGNED_LAYER_ID && layer->bgColorAlpha != 0) {
196 LayerCreationArgs backgroundLayerArgs{nullptr,
197 nullptr,
198 layer->name + "BackgroundColorLayer",
199 ISurfaceComposerClient::eFXSurfaceEffect,
200 {}};
201 std::vector<std::unique_ptr<RequestedLayerState>> newLayers;
202 newLayers.emplace_back(
203 std::make_unique<RequestedLayerState>(backgroundLayerArgs));
204 RequestedLayerState* backgroundLayer = newLayers.back().get();
205 backgroundLayer->handleAlive = false;
206 backgroundLayer->parentId = layer->id;
207 backgroundLayer->z = std::numeric_limits<int32_t>::min();
208 backgroundLayer->color.rgb = layer->color.rgb;
209 backgroundLayer->color.a = layer->bgColorAlpha;
210 backgroundLayer->dataspace = layer->bgColorDataspace;
211
212 layer->bgColorLayerId = backgroundLayer->id;
213 addLayers({std::move(newLayers)});
214 } else if (layer->bgColorLayerId != UNASSIGNED_LAYER_ID &&
215 layer->bgColorAlpha == 0) {
216 RequestedLayerState* bgColorLayer = getLayerFromId(layer->bgColorLayerId);
217 bgColorLayer->parentId = UNASSIGNED_LAYER_ID;
218 onHandlesDestroyed({layer->bgColorLayerId});
219 } else if (layer->bgColorLayerId != UNASSIGNED_LAYER_ID) {
220 RequestedLayerState* bgColorLayer = getLayerFromId(layer->bgColorLayerId);
221 bgColorLayer->color.rgb = layer->color.rgb;
222 bgColorLayer->color.a = layer->bgColorAlpha;
223 bgColorLayer->dataspace = layer->bgColorDataspace;
224 mGlobalChanges |= RequestedLayerState::Changes::Content;
225 }
226 }
227
228 if (oldParentId != layer->parentId) {
229 unlinkLayer(oldParentId, layer->id);
Vishnu Nair04f89692022-11-16 23:21:05 +0000230 layer->parentId = linkLayer(layer->parentId, layer->id);
Vishnu Naira9c43762023-01-27 19:10:25 +0000231 if (oldParentId == UNASSIGNED_LAYER_ID) {
232 updateDisplayMirrorLayers(*layer);
233 }
234 }
235 if (layer->what & layer_state_t::eLayerStackChanged && layer->isRoot()) {
236 updateDisplayMirrorLayers(*layer);
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000237 }
238 if (oldRelativeParentId != layer->relativeParentId) {
239 unlinkLayer(oldRelativeParentId, layer->id);
Vishnu Nair04f89692022-11-16 23:21:05 +0000240 layer->relativeParentId = linkLayer(layer->relativeParentId, layer->id);
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000241 }
242 if (oldTouchCropId != layer->touchCropId) {
243 unlinkLayer(oldTouchCropId, layer->id);
Vishnu Nair04f89692022-11-16 23:21:05 +0000244 layer->touchCropId = linkLayer(layer->touchCropId, layer->id);
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000245 }
246
Vishnu Nair8fc721b2022-12-22 20:06:32 +0000247 mGlobalChanges |= layer->changes;
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000248 }
249 }
250}
251
252void LayerLifecycleManager::commitChanges() {
253 for (auto& layer : mLayers) {
254 if (layer->changes.test(RequestedLayerState::Changes::Created)) {
255 for (auto listener : mListeners) {
256 listener->onLayerAdded(*layer);
257 }
258 }
259 layer->what = 0;
260 layer->changes.clear();
261 }
262
263 for (auto& destroyedLayer : mDestroyedLayers) {
264 if (destroyedLayer->changes.test(RequestedLayerState::Changes::Created)) {
265 for (auto listener : mListeners) {
266 listener->onLayerAdded(*destroyedLayer);
267 }
268 }
269
270 for (auto listener : mListeners) {
271 listener->onLayerDestroyed(*destroyedLayer);
272 }
273 }
274 mDestroyedLayers.clear();
275 mGlobalChanges.clear();
276}
277
278void LayerLifecycleManager::addLifecycleListener(std::shared_ptr<ILifecycleListener> listener) {
279 mListeners.emplace_back(std::move(listener));
280}
281
282void LayerLifecycleManager::removeLifecycleListener(std::shared_ptr<ILifecycleListener> listener) {
283 swapErase(mListeners, listener);
284}
285
286const std::vector<std::unique_ptr<RequestedLayerState>>& LayerLifecycleManager::getLayers() const {
287 return mLayers;
288}
289
290const std::vector<std::unique_ptr<RequestedLayerState>>& LayerLifecycleManager::getDestroyedLayers()
291 const {
292 return mDestroyedLayers;
293}
294
295const ftl::Flags<RequestedLayerState::Changes> LayerLifecycleManager::getGlobalChanges() const {
296 return mGlobalChanges;
297}
298
299RequestedLayerState* LayerLifecycleManager::getLayerFromId(uint32_t id) {
300 if (id == UNASSIGNED_LAYER_ID) {
301 return nullptr;
302 }
303 auto it = mIdToLayer.find(id);
304 if (it == mIdToLayer.end()) {
305 return nullptr;
306 }
307 return &it->second.owner;
308}
309
310std::vector<uint32_t>* LayerLifecycleManager::getLinkedLayersFromId(uint32_t id) {
311 if (id == UNASSIGNED_LAYER_ID) {
312 return nullptr;
313 }
314 auto it = mIdToLayer.find(id);
315 if (it == mIdToLayer.end()) {
316 return nullptr;
317 }
318 return &it->second.references;
319}
320
Vishnu Nair04f89692022-11-16 23:21:05 +0000321uint32_t LayerLifecycleManager::linkLayer(uint32_t layerId, uint32_t layerToLink) {
322 if (layerId == UNASSIGNED_LAYER_ID) {
323 return UNASSIGNED_LAYER_ID;
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000324 }
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000325
326 std::vector<uint32_t>* linkedLayers = getLinkedLayersFromId(layerId);
327 if (!linkedLayers) {
Vishnu Nair04f89692022-11-16 23:21:05 +0000328 ALOGV("Could not find layer id %d to link %d. Parent is probably destroyed", layerId,
329 layerToLink);
330 return UNASSIGNED_LAYER_ID;
331 }
332 linkedLayers->emplace_back(layerToLink);
333 return layerId;
334}
335
336uint32_t LayerLifecycleManager::unlinkLayer(uint32_t layerId, uint32_t linkedLayer) {
337 std::vector<uint32_t>* linkedLayers = getLinkedLayersFromId(layerId);
338 if (!linkedLayers) {
339 return UNASSIGNED_LAYER_ID;
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000340 }
341 swapErase(*linkedLayers, linkedLayer);
Vishnu Nair04f89692022-11-16 23:21:05 +0000342 return UNASSIGNED_LAYER_ID;
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000343}
344
Vishnu Naira9c43762023-01-27 19:10:25 +0000345std::vector<uint32_t> LayerLifecycleManager::unlinkLayers(const std::vector<uint32_t>& layerIds,
346 uint32_t linkedLayer) {
347 for (uint32_t layerId : layerIds) {
348 unlinkLayer(layerId, linkedLayer);
349 }
350 return {};
351}
352
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000353std::string LayerLifecycleManager::References::getDebugString() const {
354 std::string debugInfo = owner.name + "[" + std::to_string(owner.id) + "] refs:";
355 std::for_each(references.begin(), references.end(),
356 [&debugInfo = debugInfo](const uint32_t& reference) mutable {
357 debugInfo += std::to_string(reference) + ",";
358 });
359 return debugInfo;
360}
361
Vishnu Nair04f89692022-11-16 23:21:05 +0000362void LayerLifecycleManager::fixRelativeZLoop(uint32_t relativeRootId) {
363 auto it = mIdToLayer.find(relativeRootId);
364 if (it == mIdToLayer.end()) {
365 return;
366 }
367 RequestedLayerState& layer = it->second.owner;
368 layer.relativeParentId = unlinkLayer(layer.relativeParentId, layer.id);
369 layer.changes |=
370 RequestedLayerState::Changes::Hierarchy | RequestedLayerState::Changes::RelativeParent;
371 mGlobalChanges |= RequestedLayerState::Changes::Hierarchy;
372}
373
Vishnu Naira9c43762023-01-27 19:10:25 +0000374// Some layers mirror the entire display stack. Since we don't have a single root layer per display
375// we have to track all these layers and update what they mirror when the list of root layers
376// on a display changes. This function walks through the list of display mirroring layers
377// and updates its list of layers that its mirroring. This function should be called when a new
378// root layer is added, removed or moved to another display.
379void LayerLifecycleManager::updateDisplayMirrorLayers(RequestedLayerState& rootLayer) {
380 for (uint32_t mirrorLayerId : mDisplayMirroringLayers) {
381 RequestedLayerState* mirrorLayer = getLayerFromId(mirrorLayerId);
382 bool canBeMirrored =
383 rootLayer.isRoot() && rootLayer.layerStack == mirrorLayer->layerStackToMirror;
384 bool currentlyMirrored =
385 std::find(mirrorLayer->mirrorIds.begin(), mirrorLayer->mirrorIds.end(),
386 rootLayer.id) != mirrorLayer->mirrorIds.end();
387
388 if (canBeMirrored && !currentlyMirrored) {
389 mirrorLayer->mirrorIds.emplace_back(rootLayer.id);
390 linkLayer(rootLayer.id, mirrorLayer->id);
391 mirrorLayer->changes |= RequestedLayerState::Changes::Mirror;
392 } else if (!canBeMirrored && currentlyMirrored) {
393 swapErase(mirrorLayer->mirrorIds, rootLayer.id);
394 unlinkLayer(rootLayer.id, mirrorLayer->id);
395 mirrorLayer->changes |= RequestedLayerState::Changes::Mirror;
396 }
397 }
398}
399
Vishnu Nairdc4d31b2022-11-17 03:20:58 +0000400} // namespace android::surfaceflinger::frontend