Layer.cpp revision 792e529dee5b6cf839b982b4b06a37fbf1d3e28a
1edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project/* 2edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project 3edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * 4edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 5edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * you may not use this file except in compliance with the License. 6edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * You may obtain a copy of the License at 7edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * 8edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 9edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * 10edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 11edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 12edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * See the License for the specific language governing permissions and 14edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project * limitations under the License. 15edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project */ 16edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 171c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis#define ATRACE_TAG ATRACE_TAG_GRAPHICS 181c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis 19edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <stdlib.h> 20edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <stdint.h> 21edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <sys/types.h> 2213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian#include <math.h> 23edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 24a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian#include <cutils/compiler.h> 25076b1cc3a9b90aa5b381a1ed268ca0b548444c9bMathias Agopian#include <cutils/native_handle.h> 26a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian#include <cutils/properties.h> 27edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 28edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <utils/Errors.h> 29edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <utils/Log.h> 30399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall#include <utils/NativeHandle.h> 31edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <utils/StopWatch.h> 321c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis#include <utils/Trace.h> 33edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 343330b203039dea366d4981db1408a460134b2d2cMathias Agopian#include <ui/GraphicBuffer.h> 35edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include <ui/PixelFormat.h> 369cce325fae8adcf7560a28eef394489f09bad74dMathias Agopian 376b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza#include <gui/BufferItem.h> 3890ac799241f077a7b7e6c1875fd933864c8dd2a7Mathias Agopian#include <gui/Surface.h> 39edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 40edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include "clz.h" 413e25fd8609b100a75721be82d1d499f0ae9083cbMathias Agopian#include "Colorizer.h" 420f2f5ff75b7b48ceb64270655ee6b62d09bf4d00Mathias Agopian#include "DisplayDevice.h" 43edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include "Layer.h" 44b9b088375d33a87b201cdbe18be71802e2607717Dan Stoza#include "MonitoredProducer.h" 45edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#include "SurfaceFlinger.h" 46edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 471b03149f3533db04e72e088d3fdd09d0087ca594Mathias Agopian#include "DisplayHardware/HWComposer.h" 481b03149f3533db04e72e088d3fdd09d0087ca594Mathias Agopian 49875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian#include "RenderEngine/RenderEngine.h" 50875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian 51edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project#define DEBUG_RESIZE 0 52edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 53edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Projectnamespace android { 54edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 55edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project// --------------------------------------------------------------------------- 56edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 5713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianint32_t Layer::sSequence = 1; 5813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 594d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias AgopianLayer::Layer(SurfaceFlinger* flinger, const sp<Client>& client, 604d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian const String8& name, uint32_t w, uint32_t h, uint32_t flags) 6113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian : contentDirty(false), 6213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian sequence(uint32_t(android_atomic_inc(&sSequence))), 6313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFlinger(flinger), 64a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian mTextureName(-1U), 6513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mPremultipliedAlpha(true), 6613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mName("unnamed"), 6713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFormat(PIXEL_FORMAT_NONE), 6813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mTransactionFlags(0), 697dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mPendingStateMutex(), 707dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mPendingStates(), 71a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian mQueuedFrames(0), 72399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall mSidebandStreamChanged(false), 73a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian mCurrentTransform(0), 74933389f75814bb62e8153528f9cff2cb329b77dfMathias Agopian mCurrentScalingMode(NATIVE_WINDOW_SCALING_MODE_FREEZE), 75a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian mCurrentOpacity(true), 76cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mCurrentFrameNumber(0), 774d143eed994778d37eb09bb5d452c26f12bca6e1Mathias Agopian mRefreshPending(false), 7882d7ab6c7e0cf971e515134ccf072682dd1a2cdbMathias Agopian mFrameLatencyNeeded(false), 7913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFiltering(false), 8013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mNeedsFiltering(false), 815cdc8994a0ecd751a6350b16a1bef8b6b0d09b11Mathias Agopian mMesh(Mesh::TRIANGLE_FAN, 4, 2, 2), 8213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mProtectedByApp(false), 8313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mHasSurface(false), 8403414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews mClientRef(client), 85a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mPotentialCursor(false), 86a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mQueueItemLock(), 87a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mQueueItemCondition(), 88a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mQueueItems(), 8965476f3332641066a99e22338bf5cf49ce4af642Dan Stoza mLastFrameNumberReceived(0), 9004839abb2dbfe7afe57ccc91902870aab52d30b8Pablo Ceballos mUpdateTexImageFailed(false), 9104839abb2dbfe7afe57ccc91902870aab52d30b8Pablo Ceballos mSingleBufferMode(false) 92edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project{ 93a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian mCurrentCrop.makeInvalid(); 943f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian mFlinger->getRenderEngine().genTextures(1, &mTextureName); 9549457ac092071a8f964f7f69156093657ccdc3d0Mathias Agopian mTexture.init(Texture::TEXTURE_EXTERNAL, mTextureName); 964d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 974d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian uint32_t layerFlags = 0; 984d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian if (flags & ISurfaceComposerClient::eHidden) 994125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden layerFlags |= layer_state_t::eLayerHidden; 1004125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden if (flags & ISurfaceComposerClient::eOpaque) 1014125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden layerFlags |= layer_state_t::eLayerOpaque; 102231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza if (flags & ISurfaceComposerClient::eSecure) 103231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza layerFlags |= layer_state_t::eLayerSecure; 1044d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 1054d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian if (flags & ISurfaceComposerClient::eNonPremultiplied) 1064d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mPremultipliedAlpha = false; 1074d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 1084d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mName = name; 1094d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 1104d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.active.w = w; 1114d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.active.h = h; 1124d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.active.crop.makeInvalid(); 1134d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.z = 0; 1144d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.alpha = 0xFF; 1154d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.layerStack = 0; 1164d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.flags = layerFlags; 1174d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.sequence = 0; 1184d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.transform.set(0, 0); 1194d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mCurrentState.requested = mCurrentState.active; 1204d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 1214d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian // drawing state & current state are identical 1224d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mDrawingState = mCurrentState; 1236547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis 1246547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis nsecs_t displayPeriod = 1256547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis flinger->getHwComposer().getRefreshPeriod(HWC_DISPLAY_PRIMARY); 1266547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis mFrameTracker.setDisplayRefreshPeriod(displayPeriod); 127e8696a40e09b24b634214684d18526187b316a2fJamie Gennis} 128e8696a40e09b24b634214684d18526187b316a2fJamie Gennis 1293f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopianvoid Layer::onFirstRef() { 130bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden // Creates a custom BufferQueue for SurfaceFlingerConsumer to use 131b3d0bdf0dbc19f0a0d7d924693025371e24828fdDan Stoza sp<IGraphicBufferProducer> producer; 132b3d0bdf0dbc19f0a0d7d924693025371e24828fdDan Stoza sp<IGraphicBufferConsumer> consumer; 133b9b088375d33a87b201cdbe18be71802e2607717Dan Stoza BufferQueue::createBufferQueue(&producer, &consumer); 134b9b088375d33a87b201cdbe18be71802e2607717Dan Stoza mProducer = new MonitoredProducer(producer, mFlinger); 135b9b088375d33a87b201cdbe18be71802e2607717Dan Stoza mSurfaceFlingerConsumer = new SurfaceFlingerConsumer(consumer, mTextureName); 136bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden mSurfaceFlingerConsumer->setConsumerUsageBits(getEffectiveUsage(0)); 137399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall mSurfaceFlingerConsumer->setContentsChangedListener(this); 1384d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mSurfaceFlingerConsumer->setName(mName); 139b267579ba8dfe3f47d2a481c5a3c2254e3d565a1Daniel Lam 1407f42a9c47c5a7f40cf02032d286d6bd62f28e650Mathias Agopian#ifdef TARGET_DISABLE_TRIPLE_BUFFERING 1417f42a9c47c5a7f40cf02032d286d6bd62f28e650Mathias Agopian#warning "disabling triple buffering" 1427f42a9c47c5a7f40cf02032d286d6bd62f28e650Mathias Agopian#else 14319e3e06e3c65a7c001a6fe0971744ba5ff536515Pablo Ceballos mProducer->setMaxDequeuedBufferCount(2); 144303d538bb012e82c6b9a98c4930a03455000f761Mathias Agopian#endif 1456905205c8d130b6ea3a813c1b9283492ed183367Andy McFadden 1468430095879d2fa6878e68f8f12da4e704815ac09Mathias Agopian const sp<const DisplayDevice> hw(mFlinger->getDefaultDisplayDevice()); 1478430095879d2fa6878e68f8f12da4e704815ac09Mathias Agopian updateTransformHint(hw); 148b7e930db175c192464cebdeb49eb56cf6dd60114Mathias Agopian} 14996f0819f81293076e652792794a961543e6750d7Mathias Agopian 1504d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias AgopianLayer::~Layer() { 151cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza for (auto& point : mRemoteSyncPoints) { 152cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza point->setTransactionApplied(); 153cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 154921e6ac4b7610a178285898d191eb0e3afe906c0Mathias Agopian mFlinger->deleteTextureAsync(mTextureName); 1556547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis mFrameTracker.logAndResetStats(mName); 15696f0819f81293076e652792794a961543e6750d7Mathias Agopian} 15796f0819f81293076e652792794a961543e6750d7Mathias Agopian 15813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 15913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// callbacks 16013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 16113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 162c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::onLayerDisplayed(const sp<const DisplayDevice>& /* hw */, 16313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian HWComposer::HWCLayerInterface* layer) { 16413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (layer) { 16513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer->onDisplayed(); 16613f01cbdbd34779a234bc674df79e23672fd5c0bJesse Hall mSurfaceFlingerConsumer->setReleaseFence(layer->getAndResetReleaseFence()); 16713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 16813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 16913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 1706b9454d1fee0347711af1746642aa7820b1ea04dDan Stozavoid Layer::onFrameAvailable(const BufferItem& item) { 1716b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza // Add this buffer from our internal queue tracker 1726b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza { // Autolock scope 1736b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza Mutex::Autolock lock(mQueueItemLock); 174a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 175a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza // Reset the frame number tracker when we receive the first buffer after 176a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza // a frame number reset 177a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza if (item.mFrameNumber == 1) { 178a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mLastFrameNumberReceived = 0; 179a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza } 180a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 181a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza // Ensure that callbacks are handled in order 182a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza while (item.mFrameNumber != mLastFrameNumberReceived + 1) { 183a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza status_t result = mQueueItemCondition.waitRelative(mQueueItemLock, 184a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza ms2ns(500)); 185a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza if (result != NO_ERROR) { 186a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza ALOGE("[%s] Timed out waiting on callback", mName.string()); 187a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza } 188a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza } 189a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 1906b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza mQueueItems.push_back(item); 191ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza android_atomic_inc(&mQueuedFrames); 192a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 193a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza // Wake up any pending callbacks 194a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mLastFrameNumberReceived = item.mFrameNumber; 195a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza mQueueItemCondition.broadcast(); 1966b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza } 1976b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza 19899ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian mFlinger->signalLayerUpdate(); 199579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian} 200579b3f88d03d06b897b778bd11818f5104677d1dMathias Agopian 2016b9454d1fee0347711af1746642aa7820b1ea04dDan Stozavoid Layer::onFrameReplaced(const BufferItem& item) { 2027dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza { // Autolock scope 2037dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza Mutex::Autolock lock(mQueueItemLock); 204a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 2057dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // Ensure that callbacks are handled in order 2067dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza while (item.mFrameNumber != mLastFrameNumberReceived + 1) { 2077dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza status_t result = mQueueItemCondition.waitRelative(mQueueItemLock, 2087dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza ms2ns(500)); 2097dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (result != NO_ERROR) { 2107dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza ALOGE("[%s] Timed out waiting on callback", mName.string()); 2117dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 212a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza } 213a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 2147dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (mQueueItems.empty()) { 2157dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza ALOGE("Can't replace a frame on an empty queue"); 2167dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza return; 2177dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 2187dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mQueueItems.editItemAt(0) = item; 2197dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 2207dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // Wake up any pending callbacks 2217dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mLastFrameNumberReceived = item.mFrameNumber; 2227dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mQueueItemCondition.broadcast(); 2236b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza } 2246b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza} 2256b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza 226399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hallvoid Layer::onSidebandStreamChanged() { 227399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall if (android_atomic_release_cas(false, true, &mSidebandStreamChanged) == 0) { 228399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall // mSidebandStreamChanged was false 229399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall mFlinger->signalLayerUpdate(); 230399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall } 231399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall} 232399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall 2336710604286401d4205c27235a252dd0e5008cc08Mathias Agopian// called with SurfaceFlinger::mStateLock from the drawing thread after 2346710604286401d4205c27235a252dd0e5008cc08Mathias Agopian// the layer has been remove from the current state list (and just before 2356710604286401d4205c27235a252dd0e5008cc08Mathias Agopian// it's removed from the drawing state list) 23613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::onRemoved() { 237e338df1c2ff4ed2cd575a0e3193ef77c9cd9cb72Pablo Ceballos sp<Client> c(mClientRef.promote()); 238e338df1c2ff4ed2cd575a0e3193ef77c9cd9cb72Pablo Ceballos if (c != 0) { 239e338df1c2ff4ed2cd575a0e3193ef77c9cd9cb72Pablo Ceballos c->detachLayer(this); 240e338df1c2ff4ed2cd575a0e3193ef77c9cd9cb72Pablo Ceballos } 241bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden mSurfaceFlingerConsumer->abandon(); 24248d819a1315f7d1b5abfec9d4fd34fb5aed27b1dMathias Agopian} 243cbb288bfe89f585bf48371bd31b2d4aafa32f32eMathias Agopian 24413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 24513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// set-up 24613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 24713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 2481eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopianconst String8& Layer::getName() const { 24913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return mName; 25013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 25113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 25213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianstatus_t Layer::setBuffers( uint32_t w, uint32_t h, 25313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian PixelFormat format, uint32_t flags) 254edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project{ 25513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian uint32_t const maxSurfaceDims = min( 25613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFlinger->getMaxTextureSize(), mFlinger->getMaxViewportDims()); 25713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 25813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // never allow a surface larger than what our underlying GL implementation 25913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // can handle. 26013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if ((uint32_t(w)>maxSurfaceDims) || (uint32_t(h)>maxSurfaceDims)) { 26113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian ALOGE("dimensions too large %u x %u", uint32_t(w), uint32_t(h)); 26213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return BAD_VALUE; 26313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 26413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 26513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFormat = format; 26613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 26703414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews mPotentialCursor = (flags & ISurfaceComposerClient::eCursorWindow) ? true : false; 26813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mProtectedByApp = (flags & ISurfaceComposerClient::eProtectedByApp) ? true : false; 26913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentOpacity = getOpacityForFormat(format); 27013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 27113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mSurfaceFlingerConsumer->setDefaultBufferSize(w, h); 27213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mSurfaceFlingerConsumer->setDefaultBufferFormat(format); 27313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mSurfaceFlingerConsumer->setConsumerUsageBits(getEffectiveUsage(0)); 27413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 27513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return NO_ERROR; 27613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 27713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 2787dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza/* 2797dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza * The layer handle is just a BBinder object passed to the client 2807dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza * (remote process) -- we don't keep any reference on our side such that 2817dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza * the dtor is called when the remote side let go of its reference. 2827dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza * 2837dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza * LayerCleaner ensures that mFlinger->onLayerDestroyed() is called for 2847dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza * this layer when the handle is destroyed. 2857dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza */ 2867dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stozaclass Layer::Handle : public BBinder, public LayerCleaner { 2877dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza public: 2887dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza Handle(const sp<SurfaceFlinger>& flinger, const sp<Layer>& layer) 2897dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza : LayerCleaner(flinger, layer), owner(layer) {} 2907dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 2917dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza wp<Layer> owner; 2927dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza}; 2937dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 2944d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopiansp<IBinder> Layer::getHandle() { 2954d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian Mutex::Autolock _l(mLock); 2964d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 2974d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian LOG_ALWAYS_FATAL_IF(mHasSurface, 2984d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian "Layer::getHandle() has already been called"); 2994d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 3004d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian mHasSurface = true; 3014d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian 3024d9b822e2c18142e55fe2611aa6cd7dc7d4a62c6Mathias Agopian return new Handle(mFlinger, this); 303582270d69db94286a248bd829f1ae6f910d45124Jamie Gennis} 304582270d69db94286a248bd829f1ae6f910d45124Jamie Gennis 305b9b088375d33a87b201cdbe18be71802e2607717Dan Stozasp<IGraphicBufferProducer> Layer::getProducer() const { 306b9b088375d33a87b201cdbe18be71802e2607717Dan Stoza return mProducer; 307edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project} 308edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 30913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 31013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// h/w composer set-up 31113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 31213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 313a8bca8d84b559e7dcca010f7d6514333004020c7Mathias AgopianRect Layer::getContentCrop() const { 314a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian // this is the crop rectangle that applies to the buffer 315a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian // itself (as opposed to the window) 316f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis Rect crop; 317f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis if (!mCurrentCrop.isEmpty()) { 318a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian // if the buffer crop is defined, we use that 319f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis crop = mCurrentCrop; 320a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian } else if (mActiveBuffer != NULL) { 321a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian // otherwise we use the whole buffer 322a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian crop = mActiveBuffer->getBounds(); 323f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis } else { 324a8bca8d84b559e7dcca010f7d6514333004020c7Mathias Agopian // if we don't have a buffer yet, we use an empty/invalid crop 3254fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian crop.makeInvalid(); 326f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis } 327f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis return crop; 328f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis} 329f15a83f5814219c167f87cb8aaea622fc8493499Jamie Gennis 330f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopianstatic Rect reduce(const Rect& win, const Region& exclude) { 331f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian if (CC_LIKELY(exclude.isEmpty())) { 332f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian return win; 333f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian } 334f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian if (exclude.isRect()) { 335f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian return win.reduce(exclude.getBounds()); 336f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian } 337f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian return Region(win).subtract(exclude).getBounds(); 338f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian} 339f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian 34013127d8921356dff794250e04208c3ed60b3a3dfMathias AgopianRect Layer::computeBounds() const { 3411eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const Layer::State& s(getDrawingState()); 3426c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine return computeBounds(s.activeTransparentRegion); 3436c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine} 3446c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine 3456c925ede620f4080227bb1fe8a41e4b4502348f8Michael LentineRect Layer::computeBounds(const Region& activeTransparentRegion) const { 3466c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine const Layer::State& s(getDrawingState()); 34713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian Rect win(s.active.w, s.active.h); 34813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (!s.active.crop.isEmpty()) { 34913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian win.intersect(s.active.crop, &win); 35013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 3516c7f25afb75ac155bad0b3bc17c0089d0337d060Mathias Agopian // subtract the transparent region and snap to the bounds 3526c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine return reduce(win, activeTransparentRegion); 35313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 35413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 3556b44267a3beb457e220cad0666c039d3a765cdb2Mathias AgopianFloatRect Layer::computeCrop(const sp<const DisplayDevice>& hw) const { 35613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // the content crop is the area of the content that gets scaled to the 35713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // layer's size. 3586b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian FloatRect crop(getContentCrop()); 35913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 36013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // the active.crop is the area of the window that gets cropped, but not 36113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // scaled in any ways. 3621eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const State& s(getDrawingState()); 36313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 36413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // apply the projection's clipping to the window crop in 36513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // layerstack space, and convert-back to layer space. 3666b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian // if there are no window scaling involved, this operation will map to full 3676b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian // pixels in the buffer. 3686b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian // FIXME: the 3 lines below can produce slightly incorrect clipping when we have 3696b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian // a viewport clipping and a window transform. we should use floating point to fix this. 3700e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian 3710e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian Rect activeCrop(s.active.w, s.active.h); 3720e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian if (!s.active.crop.isEmpty()) { 3730e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian activeCrop = s.active.crop; 3740e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian } 3750e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian 3760e8f1443b87f9009159cef6394de48894f98f826Mathias Agopian activeCrop = s.transform.transform(activeCrop); 37713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian activeCrop.intersect(hw->getViewport(), &activeCrop); 37813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian activeCrop = s.transform.inverse().transform(activeCrop); 37913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 38028ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // This needs to be here as transform.transform(Rect) computes the 38128ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // transformed rect and then takes the bounding box of the result before 38228ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // returning. This means 38328ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // transform.inverse().transform(transform.transform(Rect)) != Rect 38428ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // in which case we need to make sure the final rect is clipped to the 38528ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // display bounds. 38613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian activeCrop.intersect(Rect(s.active.w, s.active.h), &activeCrop); 38713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 388f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian // subtract the transparent region and snap to the bounds 389f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian activeCrop = reduce(activeCrop, s.activeTransparentRegion); 390f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian 39113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (!activeCrop.isEmpty()) { 39213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // Transform the window crop to match the buffer coordinate system, 39313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // which means using the inverse of the current transform set on the 39413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // SurfaceFlingerConsumer. 3956b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian uint32_t invTransform = mCurrentTransform; 396f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine if (mSurfaceFlingerConsumer->getTransformToDisplayInverse()) { 397f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine /* 398f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine * the code below applies the display's inverse transform to the buffer 399f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine */ 400f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine uint32_t invTransformOrient = hw->getOrientationTransform(); 401f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine // calculate the inverse transform 402f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine if (invTransformOrient & NATIVE_WINDOW_TRANSFORM_ROT_90) { 403f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine invTransformOrient ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 404f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine NATIVE_WINDOW_TRANSFORM_FLIP_H; 4051440963470cda68be762957e2efb7ecbe1570366Michael Lentine // If the transform has been rotated the axis of flip has been swapped 4061440963470cda68be762957e2efb7ecbe1570366Michael Lentine // so we need to swap which flip operations we are performing 4071440963470cda68be762957e2efb7ecbe1570366Michael Lentine bool is_h_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_H) != 0; 4081440963470cda68be762957e2efb7ecbe1570366Michael Lentine bool is_v_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_V) != 0; 4091440963470cda68be762957e2efb7ecbe1570366Michael Lentine if (is_h_flipped != is_v_flipped) { 4101440963470cda68be762957e2efb7ecbe1570366Michael Lentine invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 4111440963470cda68be762957e2efb7ecbe1570366Michael Lentine NATIVE_WINDOW_TRANSFORM_FLIP_H; 4121440963470cda68be762957e2efb7ecbe1570366Michael Lentine } 413f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine } 414f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine // and apply to the current transform 415f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine invTransform = (Transform(invTransform) * Transform(invTransformOrient)).getOrientation(); 416f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine } 417f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine 41813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian int winWidth = s.active.w; 41913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian int winHeight = s.active.h; 42013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (invTransform & NATIVE_WINDOW_TRANSFORM_ROT_90) { 4217b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine // If the activeCrop has been rotate the ends are rotated but not 4227b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine // the space itself so when transforming ends back we can't rely on 4237b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine // a modification of the axes of rotation. To account for this we 4247b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine // need to reorient the inverse rotation in terms of the current 4257b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine // axes of rotation. 4267b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine bool is_h_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_H) != 0; 4277b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine bool is_v_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_V) != 0; 4287b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine if (is_h_flipped == is_v_flipped) { 4297b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 4307b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine NATIVE_WINDOW_TRANSFORM_FLIP_H; 4317b90258c7b1b6caf7fbbf62423723d0f4cdc79aaMichael Lentine } 43213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian winWidth = s.active.h; 43313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian winHeight = s.active.w; 43413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 43513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const Rect winCrop = activeCrop.transform( 436f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine invTransform, s.active.w, s.active.h); 43713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 4386b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian // below, crop is intersected with winCrop expressed in crop's coordinate space 4396b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian float xScale = crop.getWidth() / float(winWidth); 4406b44267a3beb457e220cad0666c039d3a765cdb2Mathias Agopian float yScale = crop.getHeight() / float(winHeight); 44113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 442f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine float insetL = winCrop.left * xScale; 443f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine float insetT = winCrop.top * yScale; 444f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine float insetR = (winWidth - winCrop.right ) * xScale; 445f75514079434cefcdb746e8b083708d6de5f86ffMichael Lentine float insetB = (winHeight - winCrop.bottom) * yScale; 44613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 44713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian crop.left += insetL; 44813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian crop.top += insetT; 44913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian crop.right -= insetR; 45013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian crop.bottom -= insetB; 45113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 45213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return crop; 45313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 45413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 4554fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopianvoid Layer::setGeometry( 4564297734c1156fd8ede7e9c61b1e439f9e1c18cd9Mathias Agopian const sp<const DisplayDevice>& hw, 4574fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian HWComposer::HWCLayerInterface& layer) 458a350ff98692b3a50cad5cc93f9f83221242ca86aMathias Agopian{ 45913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer.setDefaultState(); 460a537c0f42e8077baafcbc65844adf1ec8397c040Mathias Agopian 4613e8b853d67c737abdb363f9c978e7d83eac4d888Mathias Agopian // enable this layer 4623e8b853d67c737abdb363f9c978e7d83eac4d888Mathias Agopian layer.setSkip(false); 463a350ff98692b3a50cad5cc93f9f83221242ca86aMathias Agopian 464dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis if (isSecure() && !hw->isSecure()) { 465dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis layer.setSkip(true); 466dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis } 467dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis 46813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // this gives us only the "orientation" component of the transform 4691eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const State& s(getDrawingState()); 4704125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden if (!isOpaque(s) || s.alpha != 0xFF) { 47113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer.setBlending(mPremultipliedAlpha ? 47213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian HWC_BLENDING_PREMULT : 47313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian HWC_BLENDING_COVERAGE); 47413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 47513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 47613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // apply the layer's transform, followed by the display's global transform 47713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // here we're guaranteed that the layer's transform preserves rects 4786c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine Region activeTransparentRegion(s.activeTransparentRegion); 4796c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine if (!s.active.crop.isEmpty()) { 4806c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine Rect activeCrop(s.active.crop); 4816c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeCrop = s.transform.transform(activeCrop); 4826c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeCrop.intersect(hw->getViewport(), &activeCrop); 4836c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeCrop = s.transform.inverse().transform(activeCrop); 48428ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // This needs to be here as transform.transform(Rect) computes the 48528ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // transformed rect and then takes the bounding box of the result before 48628ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // returning. This means 48728ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // transform.inverse().transform(transform.transform(Rect)) != Rect 48828ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // in which case we need to make sure the final rect is clipped to the 48928ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine // display bounds. 49028ea217ff4e0aa9b03dfc12b6f47cccc6aaaae08Michael Lentine activeCrop.intersect(Rect(s.active.w, s.active.h), &activeCrop); 4916c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine // mark regions outside the crop as transparent 4926c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeTransparentRegion.orSelf(Rect(0, 0, s.active.w, activeCrop.top)); 4936c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeTransparentRegion.orSelf(Rect(0, activeCrop.bottom, 4946c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine s.active.w, s.active.h)); 4956c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeTransparentRegion.orSelf(Rect(0, activeCrop.top, 4966c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeCrop.left, activeCrop.bottom)); 4976c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine activeTransparentRegion.orSelf(Rect(activeCrop.right, activeCrop.top, 4986c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine s.active.w, activeCrop.bottom)); 4996c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine } 5006c925ede620f4080227bb1fe8a41e4b4502348f8Michael Lentine Rect frame(s.transform.transform(computeBounds(activeTransparentRegion))); 50113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian frame.intersect(hw->getViewport(), &frame); 50213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const Transform& tr(hw->getTransform()); 50313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer.setFrame(tr.transform(frame)); 50413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer.setCrop(computeCrop(hw)); 5059f8386e1118c10dd4927f62637ec7162569bdbdcMathias Agopian layer.setPlaneAlpha(s.alpha); 5069f8386e1118c10dd4927f62637ec7162569bdbdcMathias Agopian 50729a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian /* 50829a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian * Transformations are applied in this order: 50929a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian * 1) buffer orientation/flip/mirror 51029a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian * 2) state transformation (window manager) 51129a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian * 3) layer orientation (screen orientation) 51229a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian * (NOTE: the matrices are multiplied in reverse order) 51329a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian */ 51429a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian 51529a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian const Transform bufferOrientation(mCurrentTransform); 516c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian Transform transform(tr * s.transform * bufferOrientation); 517c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 518c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian if (mSurfaceFlingerConsumer->getTransformToDisplayInverse()) { 519c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian /* 520c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian * the code below applies the display's inverse transform to the buffer 521c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian */ 522c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian uint32_t invTransform = hw->getOrientationTransform(); 5231440963470cda68be762957e2efb7ecbe1570366Michael Lentine uint32_t t_orientation = transform.getOrientation(); 524c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian // calculate the inverse transform 525c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian if (invTransform & NATIVE_WINDOW_TRANSFORM_ROT_90) { 526c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 527c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian NATIVE_WINDOW_TRANSFORM_FLIP_H; 5281440963470cda68be762957e2efb7ecbe1570366Michael Lentine // If the transform has been rotated the axis of flip has been swapped 5291440963470cda68be762957e2efb7ecbe1570366Michael Lentine // so we need to swap which flip operations we are performing 5301440963470cda68be762957e2efb7ecbe1570366Michael Lentine bool is_h_flipped = (t_orientation & NATIVE_WINDOW_TRANSFORM_FLIP_H) != 0; 5311440963470cda68be762957e2efb7ecbe1570366Michael Lentine bool is_v_flipped = (t_orientation & NATIVE_WINDOW_TRANSFORM_FLIP_V) != 0; 5321440963470cda68be762957e2efb7ecbe1570366Michael Lentine if (is_h_flipped != is_v_flipped) { 5331440963470cda68be762957e2efb7ecbe1570366Michael Lentine t_orientation ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 5341440963470cda68be762957e2efb7ecbe1570366Michael Lentine NATIVE_WINDOW_TRANSFORM_FLIP_H; 5351440963470cda68be762957e2efb7ecbe1570366Michael Lentine } 536c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian } 537c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian // and apply to the current transform 5381440963470cda68be762957e2efb7ecbe1570366Michael Lentine transform = Transform(t_orientation) * Transform(invTransform); 539c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian } 54029a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian 54129a367bb7c14c916e991a6a0028727bd06c1e16eMathias Agopian // this gives us only the "orientation" component of the transform 54213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const uint32_t orientation = transform.getOrientation(); 54313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (orientation & Transform::ROT_INVALID) { 54413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // we can only handle simple transformation 5453e8b853d67c737abdb363f9c978e7d83eac4d888Mathias Agopian layer.setSkip(true); 546a537c0f42e8077baafcbc65844adf1ec8397c040Mathias Agopian } else { 54713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer.setTransform(orientation); 548a350ff98692b3a50cad5cc93f9f83221242ca86aMathias Agopian } 549a350ff98692b3a50cad5cc93f9f83221242ca86aMathias Agopian} 550a350ff98692b3a50cad5cc93f9f83221242ca86aMathias Agopian 5514297734c1156fd8ede7e9c61b1e439f9e1c18cd9Mathias Agopianvoid Layer::setPerFrameData(const sp<const DisplayDevice>& hw, 552d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian HWComposer::HWCLayerInterface& layer) { 55313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // we have to set the visible region on every frame because 55413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // we currently free it during onLayerDisplayed(), which is called 55513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // after HWComposer::commit() -- every frame. 55613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // Apply this display's projection's viewport to the visible region 55713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // before giving it to the HWC HAL. 55813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const Transform& tr = hw->getTransform(); 55913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian Region visible = tr.transform(visibleRegion.intersect(hw->getViewport())); 56013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian layer.setVisibleRegionScreen(visible); 561db4850c01ff02bf7f936aa427e1fa8af9abc8f22Dan Stoza layer.setSurfaceDamage(surfaceDamageRegion); 562ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza 563399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall if (mSidebandStream.get()) { 564399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall layer.setSidebandStream(mSidebandStream); 565399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall } else { 566399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall // NOTE: buffer can be NULL if the client never drew into this 567399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall // layer yet, or if we ran out of memory 568399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall layer.setBuffer(mActiveBuffer); 569399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall } 570c5c5a14c06de249d8e0445fd24699e1d9aa04549Jesse Hall} 571dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall 572c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::setAcquireFence(const sp<const DisplayDevice>& /* hw */, 573d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian HWComposer::HWCLayerInterface& layer) { 574c5c5a14c06de249d8e0445fd24699e1d9aa04549Jesse Hall int fenceFd = -1; 575d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian 576d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian // TODO: there is a possible optimization here: we only need to set the 577d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian // acquire fence the first time a new buffer is acquired on EACH display. 578d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian 57903414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews if (layer.getCompositionType() == HWC_OVERLAY || layer.getCompositionType() == HWC_CURSOR_OVERLAY) { 580bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden sp<Fence> fence = mSurfaceFlingerConsumer->getCurrentFence(); 5811df8c345854155cbbcb9f80de9d12d66ea70ac08Jamie Gennis if (fence->isValid()) { 582c5c5a14c06de249d8e0445fd24699e1d9aa04549Jesse Hall fenceFd = fence->dup(); 583dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall if (fenceFd == -1) { 584dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall ALOGW("failed to dup layer fence, skipping sync: %d", errno); 585dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall } 586dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall } 587dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall } 588c5c5a14c06de249d8e0445fd24699e1d9aa04549Jesse Hall layer.setAcquireFenceFd(fenceFd); 589c7f3381c3b2945e441747130eae88214435d0819Mathias Agopian} 590c7f3381c3b2945e441747130eae88214435d0819Mathias Agopian 59103414a1cfe6c1222fd7723949bd622f9cba145aaRiley AndrewsRect Layer::getPosition( 59203414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews const sp<const DisplayDevice>& hw) 59303414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews{ 59403414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews // this gives us only the "orientation" component of the transform 59503414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews const State& s(getCurrentState()); 59603414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews 59703414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews // apply the layer's transform, followed by the display's global transform 59803414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews // here we're guaranteed that the layer's transform preserves rects 59903414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews Rect win(s.active.w, s.active.h); 60003414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews if (!s.active.crop.isEmpty()) { 60103414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews win.intersect(s.active.crop, &win); 60203414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews } 60303414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews // subtract the transparent region and snap to the bounds 60403414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews Rect bounds = reduce(win, s.activeTransparentRegion); 60503414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews Rect frame(s.transform.transform(bounds)); 60603414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews frame.intersect(hw->getViewport(), &frame); 60703414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews const Transform& tr(hw->getTransform()); 60803414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews return Rect(tr.transform(frame)); 60903414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews} 61003414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews 61113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 61213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// drawing... 61313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 61413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 61513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::draw(const sp<const DisplayDevice>& hw, const Region& clip) const { 616c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza onDraw(hw, clip, false); 61713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 61813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 619c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::draw(const sp<const DisplayDevice>& hw, 620c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza bool useIdentityTransform) const { 621c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza onDraw(hw, Region(hw->bounds()), useIdentityTransform); 62213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 62313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 624c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::draw(const sp<const DisplayDevice>& hw) const { 625c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza onDraw(hw, Region(hw->bounds()), false); 626c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza} 627c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza 628c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::onDraw(const sp<const DisplayDevice>& hw, const Region& clip, 629c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza bool useIdentityTransform) const 630edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project{ 6311c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis ATRACE_CALL(); 6321c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis 633a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian if (CC_UNLIKELY(mActiveBuffer == 0)) { 634edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project // the texture has not been created yet, this Layer has 635179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // in fact never been drawn into. This happens frequently with 636179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // SurfaceView because the WindowManager can't know when the client 637179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // has drawn the first time. 638179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian 639179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // If there is nothing under us, we paint the screen in black, otherwise 640179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // we just skip this update. 641179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian 642179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // figure out if there is something below us 643179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian Region under; 644f7ae69d4bd292110da976c8ae766a8ef083d731fMathias Agopian const SurfaceFlinger::LayerVector& drawingLayers( 645f7ae69d4bd292110da976c8ae766a8ef083d731fMathias Agopian mFlinger->mDrawingState.layersSortedByZ); 646179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian const size_t count = drawingLayers.size(); 647179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian for (size_t i=0 ; i<count ; ++i) { 64813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const sp<Layer>& layer(drawingLayers[i]); 64913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (layer.get() == static_cast<Layer const*>(this)) 650179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian break; 6514297734c1156fd8ede7e9c61b1e439f9e1c18cd9Mathias Agopian under.orSelf( hw->getTransform().transform(layer->visibleRegion) ); 652179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian } 653179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian // if not everything below us is covered, we plug the holes! 654179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian Region holes(clip.subtract(under)); 655179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian if (!holes.isEmpty()) { 6561b03149f3533db04e72e088d3fdd09d0087ca594Mathias Agopian clearWithOpenGL(hw, holes, 0, 0, 0, 1); 657179169e88e05261196b76d7ddf94aa870aafaf9aMathias Agopian } 658edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project return; 659edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project } 660a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian 66197eba8904c2f221c42a9473407223a4c3a213f75Andy McFadden // Bind the current buffer to the GL texture, and wait for it to be 66297eba8904c2f221c42a9473407223a4c3a213f75Andy McFadden // ready for us to draw into. 663bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden status_t err = mSurfaceFlingerConsumer->bindTextureImage(); 664bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden if (err != NO_ERROR) { 66597eba8904c2f221c42a9473407223a4c3a213f75Andy McFadden ALOGW("onDraw: bindTextureImage failed (err=%d)", err); 666dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall // Go ahead and draw the buffer anyway; no matter what we do the screen 667dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall // is probably going to have something visibly wrong. 668dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall } 669dc5b485f74edf2d2f31c62054eb6c180421a3adeJesse Hall 670dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis bool blackOutLayer = isProtected() || (isSecure() && !hw->isSecure()); 671dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis 672875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian RenderEngine& engine(mFlinger->getRenderEngine()); 673875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian 674dd3cb84cfbe8068790c6233b5829fae9c4a0ee93Jamie Gennis if (!blackOutLayer) { 675cbb1a95819ec302ae15e4a1162a8b1349ae5c33eJamie Gennis // TODO: we could be more subtle with isFixedSize() 676eba8c688f633f3f3f1b75c2bc64faf799dd2b5f2Mathias Agopian const bool useFiltering = getFiltering() || needsFiltering(hw) || isFixedSize(); 677cbb1a95819ec302ae15e4a1162a8b1349ae5c33eJamie Gennis 678cbb1a95819ec302ae15e4a1162a8b1349ae5c33eJamie Gennis // Query the texture matrix given our current filtering mode. 679cbb1a95819ec302ae15e4a1162a8b1349ae5c33eJamie Gennis float textureMatrix[16]; 680bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden mSurfaceFlingerConsumer->setFilteringEnabled(useFiltering); 681bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden mSurfaceFlingerConsumer->getTransformMatrix(textureMatrix); 682cbb1a95819ec302ae15e4a1162a8b1349ae5c33eJamie Gennis 683c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian if (mSurfaceFlingerConsumer->getTransformToDisplayInverse()) { 684c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 685c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian /* 686c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian * the code below applies the display's inverse transform to the texture transform 687c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian */ 688c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 689c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian // create a 4x4 transform matrix from the display transform flags 690c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian const mat4 flipH(-1,0,0,0, 0,1,0,0, 0,0,1,0, 1,0,0,1); 691c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian const mat4 flipV( 1,0,0,0, 0,-1,0,0, 0,0,1,0, 0,1,0,1); 692c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian const mat4 rot90( 0,1,0,0, -1,0,0,0, 0,0,1,0, 1,0,0,1); 693c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 694c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian mat4 tr; 695c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian uint32_t transform = hw->getOrientationTransform(); 696c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian if (transform & NATIVE_WINDOW_TRANSFORM_ROT_90) 697c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian tr = tr * rot90; 698c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian if (transform & NATIVE_WINDOW_TRANSFORM_FLIP_H) 699c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian tr = tr * flipH; 700c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian if (transform & NATIVE_WINDOW_TRANSFORM_FLIP_V) 701c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian tr = tr * flipV; 702c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 703c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian // calculate the inverse 704c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian tr = inverse(tr); 705c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 706c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian // and finally apply it to the original texture matrix 707c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian const mat4 texTransform(mat4(static_cast<const float*>(textureMatrix)) * tr); 708c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian memcpy(textureMatrix, texTransform.asArray(), sizeof(textureMatrix)); 709c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian } 710c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian 711cbb1a95819ec302ae15e4a1162a8b1349ae5c33eJamie Gennis // Set things up for texturing. 71249457ac092071a8f964f7f69156093657ccdc3d0Mathias Agopian mTexture.setDimensions(mActiveBuffer->getWidth(), mActiveBuffer->getHeight()); 71349457ac092071a8f964f7f69156093657ccdc3d0Mathias Agopian mTexture.setFiltering(useFiltering); 71449457ac092071a8f964f7f69156093657ccdc3d0Mathias Agopian mTexture.setMatrix(textureMatrix); 71549457ac092071a8f964f7f69156093657ccdc3d0Mathias Agopian 71649457ac092071a8f964f7f69156093657ccdc3d0Mathias Agopian engine.setupLayerTexturing(mTexture); 717a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian } else { 718875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian engine.setupLayerBlackedOut(); 719a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian } 720c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza drawWithOpenGL(hw, clip, useIdentityTransform); 721875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian engine.disableTexturing(); 722edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project} 723edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 72413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 725c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::clearWithOpenGL(const sp<const DisplayDevice>& hw, 726c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza const Region& /* clip */, float red, float green, float blue, 727c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza float alpha) const 72813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian{ 72919733a32799f792125913e746e8644d16f8dc223Mathias Agopian RenderEngine& engine(mFlinger->getRenderEngine()); 730c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza computeGeometry(hw, mMesh, false); 73119733a32799f792125913e746e8644d16f8dc223Mathias Agopian engine.setupFillWithColor(red, green, blue, alpha); 73219733a32799f792125913e746e8644d16f8dc223Mathias Agopian engine.drawMesh(mMesh); 73313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 73413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 73513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::clearWithOpenGL( 73613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const sp<const DisplayDevice>& hw, const Region& clip) const { 73713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian clearWithOpenGL(hw, clip, 0,0,0,0); 73813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 73913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 740c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::drawWithOpenGL(const sp<const DisplayDevice>& hw, 741c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza const Region& /* clip */, bool useIdentityTransform) const { 7421eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const State& s(getDrawingState()); 74313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 744c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza computeGeometry(hw, mMesh, useIdentityTransform); 74513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 74613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian /* 74713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * NOTE: the way we compute the texture coordinates here produces 74813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * different results than when we take the HWC path -- in the later case 74913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * the "source crop" is rounded to texel boundaries. 75013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * This can produce significantly different results when the texture 75113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * is scaled by a large amount. 75213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * 75313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * The GL code below is more logical (imho), and the difference with 75413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * HWC is due to a limitation of the HWC API to integers -- a question 755c1c05de415854eb7a13a16b7e22a22de8515123aMathias Agopian * is suspend is whether we should ignore this problem or revert to 75613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * GL composition when a buffer scaling is applied (maybe with some 75713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * minimal value)? Or, we could make GL behave like HWC -- but this feel 75813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian * like more of a hack. 75913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian */ 76013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const Rect win(computeBounds()); 76113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 7623f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian float left = float(win.left) / float(s.active.w); 7633f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian float top = float(win.top) / float(s.active.h); 7643f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian float right = float(win.right) / float(s.active.w); 7653f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian float bottom = float(win.bottom) / float(s.active.h); 76613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 767875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian // TODO: we probably want to generate the texture coords with the mesh 768875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian // here we assume that we only have 4 vertices 769ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian Mesh::VertexArray<vec2> texCoords(mMesh.getTexCoordArray<vec2>()); 770ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian texCoords[0] = vec2(left, 1.0f - top); 771ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian texCoords[1] = vec2(left, 1.0f - bottom); 772ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian texCoords[2] = vec2(right, 1.0f - bottom); 773ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian texCoords[3] = vec2(right, 1.0f - top); 77413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 775875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian RenderEngine& engine(mFlinger->getRenderEngine()); 7764125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden engine.setupLayerBlending(mPremultipliedAlpha, isOpaque(s), s.alpha); 7775cdc8994a0ecd751a6350b16a1bef8b6b0d09b11Mathias Agopian engine.drawMesh(mMesh); 778875d8e1323536e16dcfc90c9674d7ad32116a69aMathias Agopian engine.disableBlending(); 77913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 78013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 7811681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunkuint32_t Layer::getProducerStickyTransform() const { 7821681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk int producerStickyTransform = 0; 7831681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk int ret = mProducer->query(NATIVE_WINDOW_STICKY_TRANSFORM, &producerStickyTransform); 7841681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk if (ret != OK) { 7851681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk ALOGW("%s: Error %s (%d) while querying window sticky transform.", __FUNCTION__, 7861681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk strerror(-ret), ret); 7871681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk return 0; 7881681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk } 7891681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk return static_cast<uint32_t>(producerStickyTransform); 7901681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk} 7911681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk 792cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stozauint64_t Layer::getHeadFrameNumber() const { 793cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza Mutex::Autolock lock(mQueueItemLock); 794cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (!mQueueItems.empty()) { 795cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza return mQueueItems[0].mFrameNumber; 796cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } else { 797cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza return mCurrentFrameNumber; 7987dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 799cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza} 8007dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 801cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stozabool Layer::addSyncPoint(const std::shared_ptr<SyncPoint>& point) { 802cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (point->getFrameNumber() <= mCurrentFrameNumber) { 803cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // Don't bother with a SyncPoint, since we've already latched the 804cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // relevant frame 805cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza return false; 8067dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 807cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 808cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza Mutex::Autolock lock(mLocalSyncPointMutex); 809cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mLocalSyncPoints.push_back(point); 810cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza return true; 8117dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza} 8127dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 81313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::setFiltering(bool filtering) { 81413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFiltering = filtering; 81513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 81613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 81713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::getFiltering() const { 81813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return mFiltering; 81913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 82013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 821ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold// As documented in libhardware header, formats in the range 822ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold// 0x100 - 0x1FF are specific to the HAL implementation, and 823ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold// are known to have no alpha channel 824ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold// TODO: move definition for device-specific range into 825ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold// hardware.h, instead of using hard-coded values here. 826ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold#define HARDWARE_IS_DEVICE_FORMAT(f) ((f) >= 0x100 && (f) <= 0x1FF) 827ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold 8285773d3f5b2694c647e010246dff99acc70131289Mathias Agopianbool Layer::getOpacityForFormat(uint32_t format) { 829a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian if (HARDWARE_IS_DEVICE_FORMAT(format)) { 830a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian return true; 831ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold } 8325773d3f5b2694c647e010246dff99acc70131289Mathias Agopian switch (format) { 8335773d3f5b2694c647e010246dff99acc70131289Mathias Agopian case HAL_PIXEL_FORMAT_RGBA_8888: 8345773d3f5b2694c647e010246dff99acc70131289Mathias Agopian case HAL_PIXEL_FORMAT_BGRA_8888: 835dd533712f8dd21c0dadfd5ce8a0ad85aa3e96adaMathias Agopian return false; 8365773d3f5b2694c647e010246dff99acc70131289Mathias Agopian } 8375773d3f5b2694c647e010246dff99acc70131289Mathias Agopian // in all other case, we have no blending (also for unknown formats) 838dd533712f8dd21c0dadfd5ce8a0ad85aa3e96adaMathias Agopian return true; 839ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold} 840ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold 84113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// ---------------------------------------------------------------------------- 84213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// local state 84313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// ---------------------------------------------------------------------------- 84413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 845c701401f8cec2e5309f8b57e2b97baced5093274Dan Stozavoid Layer::computeGeometry(const sp<const DisplayDevice>& hw, Mesh& mesh, 846c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza bool useIdentityTransform) const 84713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian{ 8481eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const Layer::State& s(getDrawingState()); 849c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza const Transform tr(useIdentityTransform ? 850c701401f8cec2e5309f8b57e2b97baced5093274Dan Stoza hw->getTransform() : hw->getTransform() * s.transform); 85113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const uint32_t hw_h = hw->getHeight(); 85213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian Rect win(s.active.w, s.active.h); 85313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (!s.active.crop.isEmpty()) { 85413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian win.intersect(s.active.crop, &win); 85513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 8566c7f25afb75ac155bad0b3bc17c0089d0337d060Mathias Agopian // subtract the transparent region and snap to the bounds 857f3e85d432749ca77ad707bec523b67d741d43e6eMathias Agopian win = reduce(win, s.activeTransparentRegion); 8583f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian 859ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian Mesh::VertexArray<vec2> position(mesh.getPositionArray<vec2>()); 860ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian position[0] = tr.transform(win.left, win.top); 861ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian position[1] = tr.transform(win.left, win.bottom); 862ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian position[2] = tr.transform(win.right, win.bottom); 863ff2ed70fa30f04b90dd1a2c06ec2319e157152d7Mathias Agopian position[3] = tr.transform(win.right, win.top); 8643f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian for (size_t i=0 ; i<4 ; i++) { 8655cdc8994a0ecd751a6350b16a1bef8b6b0d09b11Mathias Agopian position[i].y = hw_h - position[i].y; 86613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 86713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 868ac45e6bff1b41acd35c981291b37b23f8e083ceeEric Hassold 8694125a4ffaf374ca9c0773f256998557d3325343eAndy McFaddenbool Layer::isOpaque(const Layer::State& s) const 870a7f669256f93a593c723f05784ef04d3c7d052bbMathias Agopian{ 871a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian // if we don't have a buffer yet, we're translucent regardless of the 872a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian // layer's opaque flag. 873db5230f4441fa8f120f15bdd6fcfc6e75d9c27d0Jamie Gennis if (mActiveBuffer == 0) { 874a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian return false; 875db5230f4441fa8f120f15bdd6fcfc6e75d9c27d0Jamie Gennis } 876a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian 877a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian // if the layer has the opaque flag, then we're always opaque, 878a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian // otherwise we use the current buffer's format. 8794125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden return ((s.flags & layer_state_t::eLayerOpaque) != 0) || mCurrentOpacity; 880a7f669256f93a593c723f05784ef04d3c7d052bbMathias Agopian} 881a7f669256f93a593c723f05784ef04d3c7d052bbMathias Agopian 882231160866738f6ed2175701f300fed1a8e8e02b0Dan Stozabool Layer::isSecure() const 883231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza{ 884231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza const Layer::State& s(mDrawingState); 885231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza return (s.flags & layer_state_t::eLayerSecure); 886231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza} 887231160866738f6ed2175701f300fed1a8e8e02b0Dan Stoza 8887a4d0dfd43558c299e6af6c4910ef76db9db3172Jamie Gennisbool Layer::isProtected() const 8897a4d0dfd43558c299e6af6c4910ef76db9db3172Jamie Gennis{ 890a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian const sp<GraphicBuffer>& activeBuffer(mActiveBuffer); 8917a4d0dfd43558c299e6af6c4910ef76db9db3172Jamie Gennis return (activeBuffer != 0) && 8927a4d0dfd43558c299e6af6c4910ef76db9db3172Jamie Gennis (activeBuffer->getUsage() & GRALLOC_USAGE_PROTECTED); 8937a4d0dfd43558c299e6af6c4910ef76db9db3172Jamie Gennis} 894b5b7f260da2c1a2a82e0311e2015d49a82f43667Mathias Agopian 89513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::isFixedSize() const { 89613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return mCurrentScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE; 89713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 89813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 89913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::isCropped() const { 90013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return !mCurrentCrop.isEmpty(); 90113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 90213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 90313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::needsFiltering(const sp<const DisplayDevice>& hw) const { 90413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return mNeedsFiltering || hw->needsFiltering(); 90513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 90613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 90713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::setVisibleRegion(const Region& visibleRegion) { 90813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // always called from main thread 90913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian this->visibleRegion = visibleRegion; 91013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 91113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 91213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::setCoveredRegion(const Region& coveredRegion) { 91313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // always called from main thread 91413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian this->coveredRegion = coveredRegion; 91513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 91613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 91713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::setVisibleNonTransparentRegion(const Region& 91813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setVisibleNonTransparentRegion) { 91913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // always called from main thread 92013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian this->visibleNonTransparentRegion = setVisibleNonTransparentRegion; 92113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 92213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 92313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// ---------------------------------------------------------------------------- 92413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// transaction 92513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// ---------------------------------------------------------------------------- 92613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 9277dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stozavoid Layer::pushPendingState() { 9287dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (!mCurrentState.modified) { 9297dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza return; 9307dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 9317dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 9327dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // If this transaction is waiting on the receipt of a frame, generate a sync 9337dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // point and send it to the remote layer. 9347dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (mCurrentState.handle != nullptr) { 9357dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza sp<Handle> handle = static_cast<Handle*>(mCurrentState.handle.get()); 9367dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza sp<Layer> handleLayer = handle->owner.promote(); 9377dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (handleLayer == nullptr) { 9387dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza ALOGE("[%s] Unable to promote Layer handle", mName.string()); 9397dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // If we can't promote the layer we are intended to wait on, 9407dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // then it is expired or otherwise invalid. Allow this transaction 9417dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // to be applied as per normal (no synchronization). 9427dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.handle = nullptr; 9433bddd5b7731fafd2c60e75416ccd091972d196aePablo Ceballos } else { 9443bddd5b7731fafd2c60e75416ccd091972d196aePablo Ceballos auto syncPoint = std::make_shared<SyncPoint>( 9453bddd5b7731fafd2c60e75416ccd091972d196aePablo Ceballos mCurrentState.frameNumber); 946cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (handleLayer->addSyncPoint(syncPoint)) { 947cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mRemoteSyncPoints.push_back(std::move(syncPoint)); 948cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } else { 949cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // We already missed the frame we're supposed to synchronize 950cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // on, so go ahead and apply the state update 951cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mCurrentState.handle = nullptr; 952cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 9537dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 9547dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 9557dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // Wake us up to check if the frame has been received 9567dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza setTransactionFlags(eTransactionNeeded); 9577dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 9587dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mPendingStates.push_back(mCurrentState); 9597dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza} 9607dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 9617dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stozavoid Layer::popPendingState() { 9627dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza auto oldFlags = mCurrentState.flags; 9637dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState = mPendingStates[0]; 964cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mCurrentState.flags = (oldFlags & ~mCurrentState.mask) | 9657dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza (mCurrentState.flags & mCurrentState.mask); 9667dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 9677dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mPendingStates.removeAt(0); 9687dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza} 9697dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 9707dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stozabool Layer::applyPendingStates() { 9717dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza bool stateUpdateAvailable = false; 9727dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza while (!mPendingStates.empty()) { 9737dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (mPendingStates[0].handle != nullptr) { 9747dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (mRemoteSyncPoints.empty()) { 9757dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // If we don't have a sync point for this, apply it anyway. It 9767dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // will be visually wrong, but it should keep us from getting 9777dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // into too much trouble. 9787dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza ALOGE("[%s] No local sync point found", mName.string()); 9797dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza popPendingState(); 9807dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza stateUpdateAvailable = true; 9817dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza continue; 9827dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 9837dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 984cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (mRemoteSyncPoints.front()->getFrameNumber() != 985cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mPendingStates[0].frameNumber) { 986cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza ALOGE("[%s] Unexpected sync point frame number found", 987cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mName.string()); 988cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 989cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // Signal our end of the sync point and then dispose of it 990cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mRemoteSyncPoints.front()->setTransactionApplied(); 991cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mRemoteSyncPoints.pop_front(); 992cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza continue; 993cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 994cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 9957dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (mRemoteSyncPoints.front()->frameIsAvailable()) { 9967dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // Apply the state update 9977dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza popPendingState(); 9987dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza stateUpdateAvailable = true; 9997dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 10007dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // Signal our end of the sync point and then dispose of it 10017dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mRemoteSyncPoints.front()->setTransactionApplied(); 10027dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mRemoteSyncPoints.pop_front(); 1003792e529dee5b6cf839b982b4b06a37fbf1d3e28aDan Stoza } else { 1004792e529dee5b6cf839b982b4b06a37fbf1d3e28aDan Stoza break; 10057dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 10067dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } else { 10077dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza popPendingState(); 10087dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza stateUpdateAvailable = true; 10097dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 10107dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 10117dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 10127dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // If we still have pending updates, wake SurfaceFlinger back up and point 10137dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // it at this layer so we can process them 10147dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (!mPendingStates.empty()) { 10157dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza setTransactionFlags(eTransactionNeeded); 10167dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mFlinger->setTransactionFlags(eTraversalNeeded); 10177dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 10187dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 10197dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = false; 10207dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza return stateUpdateAvailable; 10217dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza} 10227dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 10237dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stozavoid Layer::notifyAvailableFrames() { 1024cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza auto headFrameNumber = getHeadFrameNumber(); 1025cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza Mutex::Autolock lock(mLocalSyncPointMutex); 1026cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza for (auto& point : mLocalSyncPoints) { 1027cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (headFrameNumber >= point->getFrameNumber()) { 1028cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza point->setFrameAvailable(); 1029cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 10307dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 10317dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza} 10327dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 103313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianuint32_t Layer::doTransaction(uint32_t flags) { 10341c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis ATRACE_CALL(); 10351c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis 10367dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza pushPendingState(); 10377dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza if (!applyPendingStates()) { 10387dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza return 0; 10397dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 10407dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 10411eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const Layer::State& s(getDrawingState()); 10421eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const Layer::State& c(getCurrentState()); 1043edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 10441eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const bool sizeChanged = (c.requested.w != s.requested.w) || 10451eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian (c.requested.h != s.requested.h); 1046a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian 1047a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian if (sizeChanged) { 1048cbb288bfe89f585bf48371bd31b2d4aafa32f32eMathias Agopian // the size changed, we need to ask our client to request a new buffer 10499d4536835248525f32f1504a3d28d5bbfa0a2910Steve Block ALOGD_IF(DEBUG_RESIZE, 10506905205c8d130b6ea3a813c1b9283492ed183367Andy McFadden "doTransaction: geometry (layer=%p '%s'), tr=%02x, scalingMode=%d\n" 1051419e196e639c8adb875da2765abcef95017b6d4aMathias Agopian " current={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n" 1052419e196e639c8adb875da2765abcef95017b6d4aMathias Agopian " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n" 1053419e196e639c8adb875da2765abcef95017b6d4aMathias Agopian " drawing={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n" 1054419e196e639c8adb875da2765abcef95017b6d4aMathias Agopian " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n", 10551eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian this, getName().string(), mCurrentTransform, mCurrentScalingMode, 10561eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.w, c.active.h, 10571eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.crop.left, 10581eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.crop.top, 10591eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.crop.right, 10601eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.crop.bottom, 10611eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.crop.getWidth(), 10621eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.active.crop.getHeight(), 10631eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.w, c.requested.h, 10641eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.crop.left, 10651eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.crop.top, 10661eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.crop.right, 10671eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.crop.bottom, 10681eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.crop.getWidth(), 10691eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.crop.getHeight(), 10701eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.w, s.active.h, 10711eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.crop.left, 10721eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.crop.top, 10731eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.crop.right, 10741eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.crop.bottom, 10751eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.crop.getWidth(), 10761eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.active.crop.getHeight(), 10771eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.w, s.requested.h, 10781eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.crop.left, 10791eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.crop.top, 10801eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.crop.right, 10811eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.crop.bottom, 10821eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.crop.getWidth(), 10831eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian s.requested.crop.getHeight()); 1084a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian 10852a0d5b608447a880beff5149805425f02691442bJamie Gennis // record the new size, form this point on, when the client request 10862a0d5b608447a880beff5149805425f02691442bJamie Gennis // a buffer, it'll get the new size. 1087bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden mSurfaceFlingerConsumer->setDefaultBufferSize( 10881eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian c.requested.w, c.requested.h); 1089edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project } 1090cbb288bfe89f585bf48371bd31b2d4aafa32f32eMathias Agopian 10910cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian if (!isFixedSize()) { 10920cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian 10931eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const bool resizePending = (c.requested.w != c.active.w) || 10941eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian (c.requested.h != c.active.h); 10950cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian 10969e9b0445544f11fdbf21a29601567af2d1819a30Dan Stoza if (resizePending && mSidebandStream == NULL) { 109713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // don't let Layer::doTransaction update the drawing state 10980cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // if we have a pending resize, unless we are in fixed-size mode. 10990cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // the drawing state will be updated only once we receive a buffer 11000cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // with the correct size. 11010cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // 11020cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // in particular, we want to make sure the clip (which is part 11030cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // of the geometry state) is latched together with the size but is 11040cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian // latched immediately when no resizing is involved. 11059e9b0445544f11fdbf21a29601567af2d1819a30Dan Stoza // 11069e9b0445544f11fdbf21a29601567af2d1819a30Dan Stoza // If a sideband stream is attached, however, we want to skip this 11079e9b0445544f11fdbf21a29601567af2d1819a30Dan Stoza // optimization so that transactions aren't missed when a buffer 11089e9b0445544f11fdbf21a29601567af2d1819a30Dan Stoza // never arrives 11090cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian 11100cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian flags |= eDontUpdateGeometryState; 11110cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian } 11120cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian } 11130cd545f14261d829513e0d6e8fa5e4e4f3372b3dMathias Agopian 111413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // always set active to requested, unless we're asked not to 111513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // this is used by Layer, which special cases resizes. 111613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (flags & eDontUpdateGeometryState) { 111713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } else { 11181eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian Layer::State& editCurrentState(getCurrentState()); 11191eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian editCurrentState.active = c.requested; 112013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 112113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 11221eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian if (s.active != c.active) { 112313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // invalidate and recompute the visible regions if needed 112413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian flags |= Layer::eVisibleRegion; 112513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 112613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 11271eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian if (c.sequence != s.sequence) { 112813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // invalidate and recompute the visible regions if needed 112913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian flags |= eVisibleRegion; 113013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian this->contentDirty = true; 113113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 113213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // we may use linear filtering, if the matrix scales us 11331eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const uint8_t type = c.transform.getType(); 11341eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian mNeedsFiltering = (!c.transform.preserveRects() || 113513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian (type >= Transform::SCALE)); 113613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 113713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 113813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // Commit the transaction 113913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian commitTransaction(); 114013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return flags; 1141edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project} 1142edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 114313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::commitTransaction() { 114413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mDrawingState = mCurrentState; 1145a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian} 1146a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian 114713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianuint32_t Layer::getTransactionFlags(uint32_t flags) { 114813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return android_atomic_and(~flags, &mTransactionFlags) & flags; 114913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 115013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 115113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianuint32_t Layer::setTransactionFlags(uint32_t flags) { 115213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return android_atomic_or(flags, &mTransactionFlags); 115313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 115413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 115513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setPosition(float x, float y) { 115613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.transform.tx() == x && mCurrentState.transform.ty() == y) 115713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 115813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 115913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.transform.set(x, y); 11607dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 116113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 116213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 116313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 116413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setLayer(uint32_t z) { 116513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.z == z) 116613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 116713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 116813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.z = z; 11697dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 117013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 117113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 117213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 117313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setSize(uint32_t w, uint32_t h) { 117413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.requested.w == w && mCurrentState.requested.h == h) 117513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 117613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.requested.w = w; 117713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.requested.h = h; 11787dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 117913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 118013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 118113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 118213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setAlpha(uint8_t alpha) { 118313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.alpha == alpha) 118413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 118513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 118613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.alpha = alpha; 11877dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 118813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 118913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 119013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 119113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setMatrix(const layer_state_t::matrix22_t& matrix) { 119213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 119313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.transform.set( 119413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian matrix.dsdx, matrix.dsdy, matrix.dtdx, matrix.dtdy); 11957dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 119613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 119713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 119813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 119913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setTransparentRegionHint(const Region& transparent) { 12002ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian mCurrentState.requestedTransparentRegion = transparent; 12017dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 120213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 120313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 120413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 120513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setFlags(uint8_t flags, uint8_t mask) { 120613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const uint32_t newFlags = (mCurrentState.flags & ~mask) | (flags & mask); 120713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.flags == newFlags) 120813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 120913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 121013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.flags = newFlags; 12117dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.mask = mask; 12127dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 121313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 121413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 121513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 121613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setCrop(const Rect& crop) { 121713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.requested.crop == crop) 121813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 121913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 122013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.requested.crop = crop; 12217dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 122213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 122313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 122413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 122513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 122613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianbool Layer::setLayerStack(uint32_t layerStack) { 122713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mCurrentState.layerStack == layerStack) 122813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return false; 122913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.sequence++; 123013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mCurrentState.layerStack = layerStack; 12317dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 123213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian setTransactionFlags(eTransactionNeeded); 123313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return true; 1234a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian} 1235a138f89c5e78b7e8994823e97d6e860869762837Mathias Agopian 12367dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stozavoid Layer::deferTransactionUntil(const sp<IBinder>& handle, 12377dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza uint64_t frameNumber) { 12387dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.handle = handle; 12397dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.frameNumber = frameNumber; 12407dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // We don't set eTransactionNeeded, because just receiving a deferral 12417dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza // request without any other state updates shouldn't actually induce a delay 12427dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = true; 12437dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza pushPendingState(); 1244792e529dee5b6cf839b982b4b06a37fbf1d3e28aDan Stoza mCurrentState.handle = nullptr; 1245792e529dee5b6cf839b982b4b06a37fbf1d3e28aDan Stoza mCurrentState.frameNumber = 0; 12467dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza mCurrentState.modified = false; 12477dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza} 12487dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 1249ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stozavoid Layer::useSurfaceDamage() { 1250ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza if (mFlinger->mForceFullDamage) { 1251ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza surfaceDamageRegion = Region::INVALID_REGION; 1252ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza } else { 1253ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza surfaceDamageRegion = mSurfaceFlingerConsumer->getSurfaceDamage(); 1254ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza } 1255ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza} 1256ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza 1257ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stozavoid Layer::useEmptyDamage() { 1258ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza surfaceDamageRegion.clear(); 1259ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza} 1260ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza 1261edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project// ---------------------------------------------------------------------------- 1262edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project// pageflip handling... 1263edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project// ---------------------------------------------------------------------------- 1264edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 12656b9454d1fee0347711af1746642aa7820b1ea04dDan Stozabool Layer::shouldPresentNow(const DispSync& dispSync) const { 1266063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos if (mSidebandStreamChanged || mSingleBufferMode) { 1267d87defaf486ff4e9c0066754564851cfb7be49edDan Stoza return true; 1268d87defaf486ff4e9c0066754564851cfb7be49edDan Stoza } 1269d87defaf486ff4e9c0066754564851cfb7be49edDan Stoza 12706b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza Mutex::Autolock lock(mQueueItemLock); 12710eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza if (mQueueItems.empty()) { 12720eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza return false; 12730eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza } 12740eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza auto timestamp = mQueueItems[0].mTimestamp; 12756b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza nsecs_t expectedPresent = 12766b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza mSurfaceFlingerConsumer->computeExpectedPresent(dispSync); 12770eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza 12780eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza // Ignore timestamps more than a second in the future 12790eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza bool isPlausible = timestamp < (expectedPresent + s2ns(1)); 12800eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza ALOGW_IF(!isPlausible, "[%s] Timestamp %" PRId64 " seems implausible " 12810eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza "relative to expectedPresent %" PRId64, mName.string(), timestamp, 12820eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza expectedPresent); 12830eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza 12840eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza bool isDue = timestamp < expectedPresent; 12850eb2d398669bf11207c0fb22b11439250da0c8dcDan Stoza return isDue || !isPlausible; 12866b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza} 12876b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza 12884d143eed994778d37eb09bb5d452c26f12bca6e1Mathias Agopianbool Layer::onPreComposition() { 12894d143eed994778d37eb09bb5d452c26f12bca6e1Mathias Agopian mRefreshPending = false; 1290063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos return mQueuedFrames > 0 || mSidebandStreamChanged || mSingleBufferMode; 129199ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian} 129299ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian 1293d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopianvoid Layer::onPostComposition() { 1294d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian if (mFrameLatencyNeeded) { 1295bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden nsecs_t desiredPresentTime = mSurfaceFlingerConsumer->getTimestamp(); 129682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis mFrameTracker.setDesiredPresentTime(desiredPresentTime); 129782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis 1298bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden sp<Fence> frameReadyFence = mSurfaceFlingerConsumer->getCurrentFence(); 1299789a6c3f1dfe22a1ffea7f39b2098d7842cd1f30Jamie Gennis if (frameReadyFence->isValid()) { 130082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis mFrameTracker.setFrameReadyFence(frameReadyFence); 130182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis } else { 130282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis // There was no fence for this frame, so assume that it was ready 130382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis // to be presented at the desired present time. 130482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis mFrameTracker.setFrameReadyTime(desiredPresentTime); 130582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis } 130682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis 1307d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian const HWComposer& hwc = mFlinger->getHwComposer(); 130882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis sp<Fence> presentFence = hwc.getDisplayFence(HWC_DISPLAY_PRIMARY); 1309789a6c3f1dfe22a1ffea7f39b2098d7842cd1f30Jamie Gennis if (presentFence->isValid()) { 131082dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis mFrameTracker.setActualPresentFence(presentFence); 131182dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis } else { 131282dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis // The HWC doesn't support present fences, so use the refresh 131382dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis // timestamp instead. 131482dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis nsecs_t presentTime = hwc.getRefreshTimestamp(HWC_DISPLAY_PRIMARY); 131582dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis mFrameTracker.setActualPresentTime(presentTime); 131682dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis } 131782dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis 131882dbc7429f5f9f2b303b31dc5b9f2bfd1bbe6addJamie Gennis mFrameTracker.advanceFrame(); 1319d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian mFrameLatencyNeeded = false; 1320d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian } 1321d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian} 1322d3ee231eddce0b69ec5e35188dbd0f4a2c3b9ac3Mathias Agopian 1323da27af9832a0170f1fc40ef3f21371c4d30d21b3Mathias Agopianbool Layer::isVisible() const { 132413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const Layer::State& s(mDrawingState); 132513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return !(s.flags & layer_state_t::eLayerHidden) && s.alpha 1326afe3081e0e224a3d88da2e8f211e994f833cc6bbWonsik Kim && (mActiveBuffer != NULL || mSidebandStream != NULL); 1327da27af9832a0170f1fc40ef3f21371c4d30d21b3Mathias Agopian} 1328da27af9832a0170f1fc40ef3f21371c4d30d21b3Mathias Agopian 13294fec873a98f7b4380720cd1ad006f74c8cdc73daMathias AgopianRegion Layer::latchBuffer(bool& recomputeVisibleRegions) 1330edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project{ 13311c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis ATRACE_CALL(); 13321c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis 1333399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall if (android_atomic_acquire_cas(true, false, &mSidebandStreamChanged) == 0) { 1334399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall // mSidebandStreamChanged was true 1335399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall mSidebandStream = mSurfaceFlingerConsumer->getSidebandStream(); 133612e0a27aa30d9db10eafe88904d3eb8fdcbcfa71Dan Stoza if (mSidebandStream != NULL) { 133712e0a27aa30d9db10eafe88904d3eb8fdcbcfa71Dan Stoza setTransactionFlags(eTransactionNeeded); 133812e0a27aa30d9db10eafe88904d3eb8fdcbcfa71Dan Stoza mFlinger->setTransactionFlags(eTraversalNeeded); 133912e0a27aa30d9db10eafe88904d3eb8fdcbcfa71Dan Stoza } 13405bf786d8f00ff8eee64ebf330dac55e33a0f97b1Jesse Hall recomputeVisibleRegions = true; 13415bf786d8f00ff8eee64ebf330dac55e33a0f97b1Jesse Hall 13425bf786d8f00ff8eee64ebf330dac55e33a0f97b1Jesse Hall const State& s(getDrawingState()); 13435bf786d8f00ff8eee64ebf330dac55e33a0f97b1Jesse Hall return s.transform.transform(Region(Rect(s.active.w, s.active.h))); 1344399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall } 1345399184a4cd728ea1421fb0bc1722274a29e38f4aJesse Hall 13464fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian Region outDirtyRegion; 1347063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos if (mQueuedFrames > 0 || mSingleBufferMode) { 134899ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian 134999ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian // if we've already called updateTexImage() without going through 135099ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian // a composition step, we have to skip this layer at this point 135199ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian // because we cannot call updateTeximage() without a corresponding 135299ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian // compositionComplete() call. 135399ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian // we'll trigger an update in onPreComposition(). 13544d143eed994778d37eb09bb5d452c26f12bca6e1Mathias Agopian if (mRefreshPending) { 13554fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian return outDirtyRegion; 135699ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian } 135799ce5cdeb383216dee95af4d90e47406b0948ea1Mathias Agopian 1358351a513b12622781de9580b3c96fd0a8578b563bJamie Gennis // Capture the old state of the layer for comparisons later 13594125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden const State& s(getDrawingState()); 13604125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden const bool oldOpacity = isOpaque(s); 1361351a513b12622781de9580b3c96fd0a8578b563bJamie Gennis sp<GraphicBuffer> oldActiveBuffer = mActiveBuffer; 1362db5230f4441fa8f120f15bdd6fcfc6e75d9c27d0Jamie Gennis 1363bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden struct Reject : public SurfaceFlingerConsumer::BufferRejecter { 13642c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian Layer::State& front; 13652c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian Layer::State& current; 13662c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian bool& recomputeVisibleRegions; 13671681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk bool stickyTransformSet; 13682c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian Reject(Layer::State& front, Layer::State& current, 13691681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk bool& recomputeVisibleRegions, bool stickySet) 13702c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian : front(front), current(current), 13711681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk recomputeVisibleRegions(recomputeVisibleRegions), 13721681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk stickyTransformSet(stickySet) { 13732c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 13742c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 13752c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian virtual bool reject(const sp<GraphicBuffer>& buf, 137611611f9be590480d7ea27bf0153558573ddcded2Dan Stoza const BufferItem& item) { 13772c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian if (buf == NULL) { 13782c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian return false; 13792c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 13802c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 13812c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian uint32_t bufWidth = buf->getWidth(); 13822c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian uint32_t bufHeight = buf->getHeight(); 13832c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 13842c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // check that we received a buffer of the right size 13852c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // (Take the buffer's orientation into account) 13862c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian if (item.mTransform & Transform::ROT_90) { 13872c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian swap(bufWidth, bufHeight); 13882c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 13892c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 13902c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian bool isFixedSize = item.mScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE; 13912c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian if (front.active != front.requested) { 13922c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 13932c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian if (isFixedSize || 13942c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian (bufWidth == front.requested.w && 13952c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian bufHeight == front.requested.h)) 13962c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian { 13972c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // Here we pretend the transaction happened by updating the 13982c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // current and drawing states. Drawing state is only accessed 13992c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // in this thread, no need to have it locked 14002c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active = front.requested; 14012c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 14022c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // We also need to update the current state so that 14032c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // we don't end-up overwriting the drawing state with 14042c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // this stale current state during the next transaction 14052c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // 14062c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // NOTE: We don't need to hold the transaction lock here 14072c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // because State::active is only accessed from this thread. 14082c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian current.active = front.active; 14092c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 14102c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // recompute visible region 14112c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian recomputeVisibleRegions = true; 14122c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 14132c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 14142c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian ALOGD_IF(DEBUG_RESIZE, 14156905205c8d130b6ea3a813c1b9283492ed183367Andy McFadden "latchBuffer/reject: buffer (%ux%u, tr=%02x), scalingMode=%d\n" 14162c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian " drawing={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n" 14172c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n", 14186905205c8d130b6ea3a813c1b9283492ed183367Andy McFadden bufWidth, bufHeight, item.mTransform, item.mScalingMode, 14192c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.w, front.active.h, 14202c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.crop.left, 14212c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.crop.top, 14222c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.crop.right, 14232c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.crop.bottom, 14242c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.crop.getWidth(), 14252c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.crop.getHeight(), 14262c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.w, front.requested.h, 14272c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.crop.left, 14282c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.crop.top, 14292c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.crop.right, 14302c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.crop.bottom, 14312c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.crop.getWidth(), 14322c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.requested.crop.getHeight()); 14332c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 14342c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 14351681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk if (!isFixedSize && !stickyTransformSet) { 14362c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian if (front.active.w != bufWidth || 14372c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian front.active.h != bufHeight) { 14384824d40a35333182c2eb3593511b9bcbecd0a943Mathias Agopian // reject this buffer 14391681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk ALOGE("rejecting buffer: bufWidth=%d, bufHeight=%d, front.active.{w=%d, h=%d}", 14401681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk bufWidth, bufHeight, front.active.w, front.active.h); 14412c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian return true; 14422c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 14432c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 14442ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian 14452ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian // if the transparent region has changed (this test is 14462ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian // conservative, but that's fine, worst case we're doing 14472ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian // a bit of extra work), we latch the new one and we 14482ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian // trigger a visible-region recompute. 14492ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian if (!front.activeTransparentRegion.isTriviallyEqual( 14502ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian front.requestedTransparentRegion)) { 14512ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian front.activeTransparentRegion = front.requestedTransparentRegion; 14526c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian 14536c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // We also need to update the current state so that 14546c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // we don't end-up overwriting the drawing state with 14556c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // this stale current state during the next transaction 14566c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // 14576c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // NOTE: We don't need to hold the transaction lock here 14586c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // because State::active is only accessed from this thread. 14596c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian current.activeTransparentRegion = front.activeTransparentRegion; 14606c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian 14616c67f0fe457f758fc875e1178d8fd5258fd8f6dfMathias Agopian // recompute visible region 14622ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian recomputeVisibleRegions = true; 14632ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian } 14642ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian 14652c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian return false; 14662c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 14672c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian }; 14682c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 14691681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk Reject r(mDrawingState, getCurrentState(), recomputeVisibleRegions, 14701681d95989271f3a9ac0dbb93d10e4a29f2b4444Ruben Brunk getProducerStickyTransform() != 0); 14712c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian 14727dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza 1473cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // Check all of our local sync points to ensure that all transactions 1474cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // which need to have been applied prior to the frame which is about to 1475cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // be latched have signaled 1476cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 1477cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza auto headFrameNumber = getHeadFrameNumber(); 1478cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza bool matchingFramesFound = false; 1479cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza bool allTransactionsApplied = true; 14807dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza { 1481cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza Mutex::Autolock lock(mLocalSyncPointMutex); 1482cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza for (auto& point : mLocalSyncPoints) { 1483cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (point->getFrameNumber() > headFrameNumber) { 14847dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza break; 14857dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 1486cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 14877dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza matchingFramesFound = true; 1488cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 1489cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (!point->frameIsAvailable()) { 1490cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // We haven't notified the remote layer that the frame for 1491cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // this point is available yet. Notify it now, and then 1492cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // abort this attempt to latch. 1493cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza point->setFrameAvailable(); 1494cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza allTransactionsApplied = false; 1495cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza break; 1496cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 1497cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 1498cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza allTransactionsApplied &= point->transactionIsApplied(); 14997dde599bf1a0dbef7390d91c2689d506371cdbd7Dan Stoza } 1500a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza } 1501a4650a50a0b35e9e4342d6600b6eb24fd94bb8e5Dan Stoza 1502cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (matchingFramesFound && !allTransactionsApplied) { 1503cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mFlinger->signalLayerUpdate(); 1504cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza return outDirtyRegion; 1505cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 1506cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 1507063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos // This boolean is used to make sure that SurfaceFlinger's shadow copy 1508063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos // of the buffer queue isn't modified when the buffer queue is returning 1509063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos // BufferItem's that weren't actually queued. This can happen in single 1510063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos // buffer mode. 1511063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos bool queuedBuffer = false; 151241d67d7ab4da1c393497a620a116a854b3c618e7Andy McFadden status_t updateResult = mSurfaceFlingerConsumer->updateTexImage(&r, 1513063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos mFlinger->mPrimaryDispSync, &mSingleBufferMode, &queuedBuffer, 1514cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mLastFrameNumberReceived); 15151585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden if (updateResult == BufferQueue::PRESENT_LATER) { 15161585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden // Producer doesn't want buffer to be displayed yet. Signal a 15171585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden // layer update so we check again at the next opportunity. 15181585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden mFlinger->signalLayerUpdate(); 15191585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden return outDirtyRegion; 1520ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza } else if (updateResult == SurfaceFlingerConsumer::BUFFER_REJECTED) { 1521ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza // If the buffer has been rejected, remove it from the shadow queue 1522ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza // and return early 1523063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos if (queuedBuffer) { 1524063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos Mutex::Autolock lock(mQueueItemLock); 1525063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos mQueueItems.removeAt(0); 1526063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos android_atomic_dec(&mQueuedFrames); 1527063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos } 1528ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza return outDirtyRegion; 152965476f3332641066a99e22338bf5cf49ce4af642Dan Stoza } else if (updateResult != NO_ERROR || mUpdateTexImageFailed) { 153065476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // This can occur if something goes wrong when trying to create the 153165476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // EGLImage for this buffer. If this happens, the buffer has already 153265476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // been released, so we need to clean up the queue and bug out 153365476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // early. 1534063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos if (queuedBuffer) { 153565476f3332641066a99e22338bf5cf49ce4af642Dan Stoza Mutex::Autolock lock(mQueueItemLock); 153665476f3332641066a99e22338bf5cf49ce4af642Dan Stoza mQueueItems.clear(); 153765476f3332641066a99e22338bf5cf49ce4af642Dan Stoza android_atomic_and(0, &mQueuedFrames); 153865476f3332641066a99e22338bf5cf49ce4af642Dan Stoza } 153965476f3332641066a99e22338bf5cf49ce4af642Dan Stoza 154065476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // Once we have hit this state, the shadow queue may no longer 154165476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // correctly reflect the incoming BufferQueue's contents, so even if 154265476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // updateTexImage starts working, the only safe course of action is 154365476f3332641066a99e22338bf5cf49ce4af642Dan Stoza // to continue to ignore updates. 154465476f3332641066a99e22338bf5cf49ce4af642Dan Stoza mUpdateTexImageFailed = true; 154565476f3332641066a99e22338bf5cf49ce4af642Dan Stoza 154665476f3332641066a99e22338bf5cf49ce4af642Dan Stoza return outDirtyRegion; 15471585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden } 15481585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden 1549063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos if (queuedBuffer) { 1550063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos // Autolock scope 1551ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza auto currentFrameNumber = mSurfaceFlingerConsumer->getFrameNumber(); 1552ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza 15536b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza Mutex::Autolock lock(mQueueItemLock); 1554ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza 1555ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza // Remove any stale buffers that have been dropped during 1556ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza // updateTexImage 1557ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza while (mQueueItems[0].mFrameNumber != currentFrameNumber) { 1558ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza mQueueItems.removeAt(0); 1559ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza android_atomic_dec(&mQueuedFrames); 1560ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza } 1561ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza 15626b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza mQueueItems.removeAt(0); 15636b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza } 15646b9454d1fee0347711af1746642aa7820b1ea04dDan Stoza 1565ecc504043fddb7a75042ce402c67aedfac04d5e2Dan Stoza 15661585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden // Decrement the queued-frames count. Signal another event if we 15671585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden // have more frames pending. 1568063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos if ((queuedBuffer && android_atomic_dec(&mQueuedFrames) > 1) 1569063121849890da78b1ad7fb96c54c795de5d1fd6Pablo Ceballos || mSingleBufferMode) { 15701585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden mFlinger->signalLayerUpdate(); 15711585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden } 15721585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden 15731585c4d9fbbba3ba70ae625923b85cd02cb8a0fdAndy McFadden if (updateResult != NO_ERROR) { 1574a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian // something happened! 1575a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian recomputeVisibleRegions = true; 15764fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian return outDirtyRegion; 1577a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian } 1578d343e3d5e3177806205b9452b0b43907e28afd9aMathias Agopian 1579351a513b12622781de9580b3c96fd0a8578b563bJamie Gennis // update the active buffer 1580bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden mActiveBuffer = mSurfaceFlingerConsumer->getCurrentBuffer(); 1581e31564d8eb0ab67e167a888eccce20f5b4e4ef45Mathias Agopian if (mActiveBuffer == NULL) { 1582e31564d8eb0ab67e167a888eccce20f5b4e4ef45Mathias Agopian // this can only happen if the very first buffer was rejected. 15834fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian return outDirtyRegion; 1584e31564d8eb0ab67e167a888eccce20f5b4e4ef45Mathias Agopian } 1585da9584dc295cc5e6d0b49a97c1e45159249d650bMathias Agopian 15864824d40a35333182c2eb3593511b9bcbecd0a943Mathias Agopian mRefreshPending = true; 1587702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian mFrameLatencyNeeded = true; 1588e31564d8eb0ab67e167a888eccce20f5b4e4ef45Mathias Agopian if (oldActiveBuffer == NULL) { 15892c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // the first time we receive a buffer, we need to trigger a 15902c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian // geometry invalidation. 1591ab10c5804c250e7f392c8262f687766edec2e9f4Andy McFadden recomputeVisibleRegions = true; 15922c8207e9627fe6c7a90e31fae8d71ae49df56845Mathias Agopian } 1593702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian 1594bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden Rect crop(mSurfaceFlingerConsumer->getCurrentCrop()); 1595bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden const uint32_t transform(mSurfaceFlingerConsumer->getCurrentTransform()); 1596bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden const uint32_t scalingMode(mSurfaceFlingerConsumer->getCurrentScalingMode()); 1597702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian if ((crop != mCurrentCrop) || 1598702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian (transform != mCurrentTransform) || 1599702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian (scalingMode != mCurrentScalingMode)) 1600702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian { 1601702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian mCurrentCrop = crop; 1602702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian mCurrentTransform = transform; 1603702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian mCurrentScalingMode = scalingMode; 1604ab10c5804c250e7f392c8262f687766edec2e9f4Andy McFadden recomputeVisibleRegions = true; 1605702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian } 1606702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian 1607702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian if (oldActiveBuffer != NULL) { 1608e31564d8eb0ab67e167a888eccce20f5b4e4ef45Mathias Agopian uint32_t bufWidth = mActiveBuffer->getWidth(); 1609e31564d8eb0ab67e167a888eccce20f5b4e4ef45Mathias Agopian uint32_t bufHeight = mActiveBuffer->getHeight(); 1610702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian if (bufWidth != uint32_t(oldActiveBuffer->width) || 1611702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian bufHeight != uint32_t(oldActiveBuffer->height)) { 1612ab10c5804c250e7f392c8262f687766edec2e9f4Andy McFadden recomputeVisibleRegions = true; 1613702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian } 1614702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian } 1615702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian 1616702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian mCurrentOpacity = getOpacityForFormat(mActiveBuffer->format); 16174125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden if (oldOpacity != isOpaque(s)) { 1618702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian recomputeVisibleRegions = true; 1619702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian } 1620702634a4dad85cfc292618ac91eda6c00f42b7c5Mathias Agopian 1621cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza mCurrentFrameNumber = mSurfaceFlingerConsumer->getFrameNumber(); 1622cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 1623cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // Remove any sync points corresponding to the buffer which was just 1624cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // latched 1625cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza { 1626cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza Mutex::Autolock lock(mLocalSyncPointMutex); 1627cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza auto point = mLocalSyncPoints.begin(); 1628cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza while (point != mLocalSyncPoints.end()) { 1629cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if (!(*point)->frameIsAvailable() || 1630cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza !(*point)->transactionIsApplied()) { 1631cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // This sync point must have been added since we started 1632cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza // latching. Don't drop it yet. 1633cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza ++point; 1634cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza continue; 1635cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 1636cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 1637cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza if ((*point)->getFrameNumber() <= mCurrentFrameNumber) { 1638cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza point = mLocalSyncPoints.erase(point); 1639cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } else { 1640cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza ++point; 1641cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 1642cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 1643cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza } 1644cac353808ec1048333d7fd2f3d596fb4db567aa3Dan Stoza 16454fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian // FIXME: postedRegion should be dirty & bounds 16461eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian Region dirtyRegion(Rect(s.active.w, s.active.h)); 16471c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis 16484fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian // transform the dirty region to window-manager space 16491eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian outDirtyRegion = (s.transform.transform(dirtyRegion)); 1650edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project } 16514fec873a98f7b4380720cd1ad006f74c8cdc73daMathias Agopian return outDirtyRegion; 1652edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project} 1653edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 165413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianuint32_t Layer::getEffectiveUsage(uint32_t usage) const 165513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian{ 165613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // TODO: should we do something special if mSecure is set? 165713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (mProtectedByApp) { 165813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // need a hardware-protected path to external video sink 165913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian usage |= GraphicBuffer::USAGE_PROTECTED; 166013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 166103414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews if (mPotentialCursor) { 166203414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews usage |= GraphicBuffer::USAGE_CURSOR; 166303414a1cfe6c1222fd7723949bd622f9cba145aaRiley Andrews } 166413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian usage |= GraphicBuffer::USAGE_HW_COMPOSER; 166513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian return usage; 166613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 166713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 166813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopianvoid Layer::updateTransformHint(const sp<const DisplayDevice>& hw) const { 166913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian uint32_t orientation = 0; 167013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (!mFlinger->mDebugDisableTransformHint) { 167113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // The transform hint is used to improve performance, but we can 167213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // only have a single transform hint, it cannot 167313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // apply to all displays. 167413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const Transform& planeTransform(hw->getTransform()); 167513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian orientation = planeTransform.getOrientation(); 167613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian if (orientation & Transform::ROT_INVALID) { 167713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian orientation = 0; 167813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 167913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian } 168013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mSurfaceFlingerConsumer->setTransformHint(orientation); 168113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian} 168213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 168313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// ---------------------------------------------------------------------------- 168413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// debugging 168513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// ---------------------------------------------------------------------------- 168613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 16873e25fd8609b100a75721be82d1d499f0ae9083cbMathias Agopianvoid Layer::dump(String8& result, Colorizer& colorizer) const 16881b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian{ 16891eae0ee49402c39f1b08cc8fec129023f86494b7Mathias Agopian const Layer::State& s(getDrawingState()); 169013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 16913e25fd8609b100a75721be82d1d499f0ae9083cbMathias Agopian colorizer.colorize(result, Colorizer::GREEN); 169274d211ae26a0257c6075a823812e40b55aa1e653Mathias Agopian result.appendFormat( 169313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian "+ %s %p (%s)\n", 169413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian getTypeId(), this, getName().string()); 16953e25fd8609b100a75721be82d1d499f0ae9083cbMathias Agopian colorizer.reset(result); 169613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 16972ca79399b933935eb1b6c0ec1f746f8c4475369cMathias Agopian s.activeTransparentRegion.dump(result, "transparentRegion"); 169813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian visibleRegion.dump(result, "visibleRegion"); 1699ee44edd0acccbf5eaa918d75737c3b65ee04fff7Dan Stoza surfaceDamageRegion.dump(result, "surfaceDamageRegion"); 170013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian sp<Client> client(mClientRef.promote()); 170113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 170274d211ae26a0257c6075a823812e40b55aa1e653Mathias Agopian result.appendFormat( " " 170313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian "layerStack=%4d, z=%9d, pos=(%g,%g), size=(%4d,%4d), crop=(%4d,%4d,%4d,%4d), " 170413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian "isOpaque=%1d, invalidate=%1d, " 170513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian "alpha=0x%02x, flags=0x%08x, tr=[%.2f, %.2f][%.2f, %.2f]\n" 170613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian " client=%p\n", 170713127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian s.layerStack, s.z, s.transform.tx(), s.transform.ty(), s.active.w, s.active.h, 170813127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian s.active.crop.left, s.active.crop.top, 170913127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian s.active.crop.right, s.active.crop.bottom, 17104125a4ffaf374ca9c0773f256998557d3325343eAndy McFadden isOpaque(s), contentDirty, 171113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian s.alpha, s.flags, 171213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian s.transform[0][0], s.transform[0][1], 171313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian s.transform[1][0], s.transform[1][1], 171413127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian client.get()); 17151b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian 1716a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian sp<const GraphicBuffer> buf0(mActiveBuffer); 1717a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian uint32_t w0=0, h0=0, s0=0, f0=0; 17181b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian if (buf0 != 0) { 17191b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian w0 = buf0->getWidth(); 17201b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian h0 = buf0->getHeight(); 17211b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian s0 = buf0->getStride(); 1722a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian f0 = buf0->format; 17231b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian } 172474d211ae26a0257c6075a823812e40b55aa1e653Mathias Agopian result.appendFormat( 17251b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian " " 1726ad795baecccf239621cbffa0249c8e855296cae6Mathias Agopian "format=%2d, activeBuffer=[%4ux%4u:%4u,%3X]," 17276905205c8d130b6ea3a813c1b9283492ed183367Andy McFadden " queued-frames=%d, mRefreshPending=%d\n", 1728a67932fe6864ac346e7f78b86df11cf6c5344137Mathias Agopian mFormat, w0, h0, s0,f0, 17296905205c8d130b6ea3a813c1b9283492ed183367Andy McFadden mQueuedFrames, mRefreshPending); 17301b5e1021b8c9b87113b70d94dfb7b50f8c5b01b8Mathias Agopian 1731bf974abe92f7495529916fe0f483f3b56e7c30e3Andy McFadden if (mSurfaceFlingerConsumer != 0) { 173274d211ae26a0257c6075a823812e40b55aa1e653Mathias Agopian mSurfaceFlingerConsumer->dump(result, " "); 1733bb641244d7d73312dc65b8e338df18b22e335107Mathias Agopian } 1734d606de6bb6877dc4ab93ec0be0c6bda4a8ee1ce8Mathias Agopian} 1735d606de6bb6877dc4ab93ec0be0c6bda4a8ee1ce8Mathias Agopian 1736d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslavvoid Layer::dumpFrameStats(String8& result) const { 1737d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslav mFrameTracker.dumpStats(result); 173882d7ab6c7e0cf971e515134ccf072682dd1a2cdbMathias Agopian} 173982d7ab6c7e0cf971e515134ccf072682dd1a2cdbMathias Agopian 1740d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslavvoid Layer::clearFrameStats() { 1741d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslav mFrameTracker.clearStats(); 174225e66fc324bbc004fa8902b2d4699e41bb601104Mathias Agopian} 174325e66fc324bbc004fa8902b2d4699e41bb601104Mathias Agopian 17446547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennisvoid Layer::logFrameStats() { 17456547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis mFrameTracker.logAndResetStats(mName); 17466547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis} 17476547ff4327aa320fbc9635668d3fc66db7dd78f6Jamie Gennis 1748d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslavvoid Layer::getFrameStats(FrameStats* outStats) const { 1749d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslav mFrameTracker.getStats(outStats); 1750d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslav} 1751d85084b2b65828442eafaff9b811e9b6c9ca9fadSvetoslav 175213127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian// --------------------------------------------------------------------------- 175313127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian 175413127d8921356dff794250e04208c3ed60b3a3dfMathias AgopianLayer::LayerCleaner::LayerCleaner(const sp<SurfaceFlinger>& flinger, 175513127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian const sp<Layer>& layer) 175613127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian : mFlinger(flinger), mLayer(layer) { 1757b5b7f260da2c1a2a82e0311e2015d49a82f43667Mathias Agopian} 1758b5b7f260da2c1a2a82e0311e2015d49a82f43667Mathias Agopian 175913127d8921356dff794250e04208c3ed60b3a3dfMathias AgopianLayer::LayerCleaner::~LayerCleaner() { 176013127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian // destroy client resources 176113127d8921356dff794250e04208c3ed60b3a3dfMathias Agopian mFlinger->onLayerDestroyed(mLayer); 1762a45836466c301d49d8df286b5317dfa99cb83b70Mathias Agopian} 1763a45836466c301d49d8df286b5317dfa99cb83b70Mathias Agopian 1764edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project// --------------------------------------------------------------------------- 17653f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian}; // namespace android 1766edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 17673f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian#if defined(__gl_h_) 17683f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian#error "don't include gl/gl.h in this file" 17693f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian#endif 1770edbf3b6af777b721cd2a1ef461947e51e88241e1The Android Open Source Project 17713f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian#if defined(__gl2_h_) 17723f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian#error "don't include gl2/gl2.h in this file" 17733f84483382be2d528918cc1a6fbc6a7d68e0b181Mathias Agopian#endif 1774