Layer.cpp revision 6b9454d1fee0347711af1746642aa7820b1ea04d
1/* 2 * Copyright (C) 2007 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17#define ATRACE_TAG ATRACE_TAG_GRAPHICS 18 19#include <stdlib.h> 20#include <stdint.h> 21#include <sys/types.h> 22#include <math.h> 23 24#include <cutils/compiler.h> 25#include <cutils/native_handle.h> 26#include <cutils/properties.h> 27 28#include <utils/Errors.h> 29#include <utils/Log.h> 30#include <utils/NativeHandle.h> 31#include <utils/StopWatch.h> 32#include <utils/Trace.h> 33 34#include <ui/GraphicBuffer.h> 35#include <ui/PixelFormat.h> 36 37#include <gui/BufferItem.h> 38#include <gui/Surface.h> 39 40#include "clz.h" 41#include "Colorizer.h" 42#include "DisplayDevice.h" 43#include "Layer.h" 44#include "MonitoredProducer.h" 45#include "SurfaceFlinger.h" 46 47#include "DisplayHardware/HWComposer.h" 48 49#include "RenderEngine/RenderEngine.h" 50 51#define DEBUG_RESIZE 0 52 53namespace android { 54 55// --------------------------------------------------------------------------- 56 57int32_t Layer::sSequence = 1; 58 59Layer::Layer(SurfaceFlinger* flinger, const sp<Client>& client, 60 const String8& name, uint32_t w, uint32_t h, uint32_t flags) 61 : contentDirty(false), 62 sequence(uint32_t(android_atomic_inc(&sSequence))), 63 mFlinger(flinger), 64 mTextureName(-1U), 65 mPremultipliedAlpha(true), 66 mName("unnamed"), 67 mDebug(false), 68 mFormat(PIXEL_FORMAT_NONE), 69 mTransactionFlags(0), 70 mQueuedFrames(0), 71 mSidebandStreamChanged(false), 72 mCurrentTransform(0), 73 mCurrentScalingMode(NATIVE_WINDOW_SCALING_MODE_FREEZE), 74 mCurrentOpacity(true), 75 mRefreshPending(false), 76 mFrameLatencyNeeded(false), 77 mFiltering(false), 78 mNeedsFiltering(false), 79 mMesh(Mesh::TRIANGLE_FAN, 4, 2, 2), 80 mSecure(false), 81 mProtectedByApp(false), 82 mHasSurface(false), 83 mClientRef(client), 84 mPotentialCursor(false) 85{ 86 mCurrentCrop.makeInvalid(); 87 mFlinger->getRenderEngine().genTextures(1, &mTextureName); 88 mTexture.init(Texture::TEXTURE_EXTERNAL, mTextureName); 89 90 uint32_t layerFlags = 0; 91 if (flags & ISurfaceComposerClient::eHidden) 92 layerFlags |= layer_state_t::eLayerHidden; 93 if (flags & ISurfaceComposerClient::eOpaque) 94 layerFlags |= layer_state_t::eLayerOpaque; 95 96 if (flags & ISurfaceComposerClient::eNonPremultiplied) 97 mPremultipliedAlpha = false; 98 99 mName = name; 100 101 mCurrentState.active.w = w; 102 mCurrentState.active.h = h; 103 mCurrentState.active.crop.makeInvalid(); 104 mCurrentState.z = 0; 105 mCurrentState.alpha = 0xFF; 106 mCurrentState.layerStack = 0; 107 mCurrentState.flags = layerFlags; 108 mCurrentState.sequence = 0; 109 mCurrentState.transform.set(0, 0); 110 mCurrentState.requested = mCurrentState.active; 111 112 // drawing state & current state are identical 113 mDrawingState = mCurrentState; 114 115 nsecs_t displayPeriod = 116 flinger->getHwComposer().getRefreshPeriod(HWC_DISPLAY_PRIMARY); 117 mFrameTracker.setDisplayRefreshPeriod(displayPeriod); 118} 119 120void Layer::onFirstRef() { 121 // Creates a custom BufferQueue for SurfaceFlingerConsumer to use 122 sp<IGraphicBufferProducer> producer; 123 sp<IGraphicBufferConsumer> consumer; 124 BufferQueue::createBufferQueue(&producer, &consumer); 125 mProducer = new MonitoredProducer(producer, mFlinger); 126 mSurfaceFlingerConsumer = new SurfaceFlingerConsumer(consumer, mTextureName); 127 mSurfaceFlingerConsumer->setConsumerUsageBits(getEffectiveUsage(0)); 128 mSurfaceFlingerConsumer->setContentsChangedListener(this); 129 mSurfaceFlingerConsumer->setName(mName); 130 131#ifdef TARGET_DISABLE_TRIPLE_BUFFERING 132#warning "disabling triple buffering" 133 mSurfaceFlingerConsumer->setDefaultMaxBufferCount(2); 134#else 135 mSurfaceFlingerConsumer->setDefaultMaxBufferCount(3); 136#endif 137 138 const sp<const DisplayDevice> hw(mFlinger->getDefaultDisplayDevice()); 139 updateTransformHint(hw); 140} 141 142Layer::~Layer() { 143 sp<Client> c(mClientRef.promote()); 144 if (c != 0) { 145 c->detachLayer(this); 146 } 147 mFlinger->deleteTextureAsync(mTextureName); 148 mFrameTracker.logAndResetStats(mName); 149} 150 151// --------------------------------------------------------------------------- 152// callbacks 153// --------------------------------------------------------------------------- 154 155void Layer::onLayerDisplayed(const sp<const DisplayDevice>& /* hw */, 156 HWComposer::HWCLayerInterface* layer) { 157 if (layer) { 158 layer->onDisplayed(); 159 mSurfaceFlingerConsumer->setReleaseFence(layer->getAndResetReleaseFence()); 160 } 161} 162 163void Layer::onFrameAvailable(const BufferItem& item) { 164 // Add this buffer from our internal queue tracker 165 { // Autolock scope 166 Mutex::Autolock lock(mQueueItemLock); 167 mQueueItems.push_back(item); 168 } 169 170 android_atomic_inc(&mQueuedFrames); 171 mFlinger->signalLayerUpdate(); 172} 173 174void Layer::onFrameReplaced(const BufferItem& item) { 175 Mutex::Autolock lock(mQueueItemLock); 176 if (mQueueItems.empty()) { 177 ALOGE("Can't replace a frame on an empty queue"); 178 return; 179 } 180 mQueueItems.editItemAt(0) = item; 181} 182 183void Layer::onSidebandStreamChanged() { 184 if (android_atomic_release_cas(false, true, &mSidebandStreamChanged) == 0) { 185 // mSidebandStreamChanged was false 186 mFlinger->signalLayerUpdate(); 187 } 188} 189 190// called with SurfaceFlinger::mStateLock from the drawing thread after 191// the layer has been remove from the current state list (and just before 192// it's removed from the drawing state list) 193void Layer::onRemoved() { 194 mSurfaceFlingerConsumer->abandon(); 195} 196 197// --------------------------------------------------------------------------- 198// set-up 199// --------------------------------------------------------------------------- 200 201const String8& Layer::getName() const { 202 return mName; 203} 204 205status_t Layer::setBuffers( uint32_t w, uint32_t h, 206 PixelFormat format, uint32_t flags) 207{ 208 uint32_t const maxSurfaceDims = min( 209 mFlinger->getMaxTextureSize(), mFlinger->getMaxViewportDims()); 210 211 // never allow a surface larger than what our underlying GL implementation 212 // can handle. 213 if ((uint32_t(w)>maxSurfaceDims) || (uint32_t(h)>maxSurfaceDims)) { 214 ALOGE("dimensions too large %u x %u", uint32_t(w), uint32_t(h)); 215 return BAD_VALUE; 216 } 217 218 mFormat = format; 219 220 mPotentialCursor = (flags & ISurfaceComposerClient::eCursorWindow) ? true : false; 221 mSecure = (flags & ISurfaceComposerClient::eSecure) ? true : false; 222 mProtectedByApp = (flags & ISurfaceComposerClient::eProtectedByApp) ? true : false; 223 mCurrentOpacity = getOpacityForFormat(format); 224 225 mSurfaceFlingerConsumer->setDefaultBufferSize(w, h); 226 mSurfaceFlingerConsumer->setDefaultBufferFormat(format); 227 mSurfaceFlingerConsumer->setConsumerUsageBits(getEffectiveUsage(0)); 228 229 return NO_ERROR; 230} 231 232sp<IBinder> Layer::getHandle() { 233 Mutex::Autolock _l(mLock); 234 235 LOG_ALWAYS_FATAL_IF(mHasSurface, 236 "Layer::getHandle() has already been called"); 237 238 mHasSurface = true; 239 240 /* 241 * The layer handle is just a BBinder object passed to the client 242 * (remote process) -- we don't keep any reference on our side such that 243 * the dtor is called when the remote side let go of its reference. 244 * 245 * LayerCleaner ensures that mFlinger->onLayerDestroyed() is called for 246 * this layer when the handle is destroyed. 247 */ 248 249 class Handle : public BBinder, public LayerCleaner { 250 wp<const Layer> mOwner; 251 public: 252 Handle(const sp<SurfaceFlinger>& flinger, const sp<Layer>& layer) 253 : LayerCleaner(flinger, layer), mOwner(layer) { 254 } 255 }; 256 257 return new Handle(mFlinger, this); 258} 259 260sp<IGraphicBufferProducer> Layer::getProducer() const { 261 return mProducer; 262} 263 264// --------------------------------------------------------------------------- 265// h/w composer set-up 266// --------------------------------------------------------------------------- 267 268Rect Layer::getContentCrop() const { 269 // this is the crop rectangle that applies to the buffer 270 // itself (as opposed to the window) 271 Rect crop; 272 if (!mCurrentCrop.isEmpty()) { 273 // if the buffer crop is defined, we use that 274 crop = mCurrentCrop; 275 } else if (mActiveBuffer != NULL) { 276 // otherwise we use the whole buffer 277 crop = mActiveBuffer->getBounds(); 278 } else { 279 // if we don't have a buffer yet, we use an empty/invalid crop 280 crop.makeInvalid(); 281 } 282 return crop; 283} 284 285static Rect reduce(const Rect& win, const Region& exclude) { 286 if (CC_LIKELY(exclude.isEmpty())) { 287 return win; 288 } 289 if (exclude.isRect()) { 290 return win.reduce(exclude.getBounds()); 291 } 292 return Region(win).subtract(exclude).getBounds(); 293} 294 295Rect Layer::computeBounds() const { 296 const Layer::State& s(getDrawingState()); 297 return computeBounds(s.activeTransparentRegion); 298} 299 300Rect Layer::computeBounds(const Region& activeTransparentRegion) const { 301 const Layer::State& s(getDrawingState()); 302 Rect win(s.active.w, s.active.h); 303 if (!s.active.crop.isEmpty()) { 304 win.intersect(s.active.crop, &win); 305 } 306 // subtract the transparent region and snap to the bounds 307 return reduce(win, activeTransparentRegion); 308} 309 310FloatRect Layer::computeCrop(const sp<const DisplayDevice>& hw) const { 311 // the content crop is the area of the content that gets scaled to the 312 // layer's size. 313 FloatRect crop(getContentCrop()); 314 315 // the active.crop is the area of the window that gets cropped, but not 316 // scaled in any ways. 317 const State& s(getDrawingState()); 318 319 // apply the projection's clipping to the window crop in 320 // layerstack space, and convert-back to layer space. 321 // if there are no window scaling involved, this operation will map to full 322 // pixels in the buffer. 323 // FIXME: the 3 lines below can produce slightly incorrect clipping when we have 324 // a viewport clipping and a window transform. we should use floating point to fix this. 325 326 Rect activeCrop(s.active.w, s.active.h); 327 if (!s.active.crop.isEmpty()) { 328 activeCrop = s.active.crop; 329 } 330 331 activeCrop = s.transform.transform(activeCrop); 332 activeCrop.intersect(hw->getViewport(), &activeCrop); 333 activeCrop = s.transform.inverse().transform(activeCrop); 334 335 // paranoia: make sure the window-crop is constrained in the 336 // window's bounds 337 activeCrop.intersect(Rect(s.active.w, s.active.h), &activeCrop); 338 339 // subtract the transparent region and snap to the bounds 340 activeCrop = reduce(activeCrop, s.activeTransparentRegion); 341 342 if (!activeCrop.isEmpty()) { 343 // Transform the window crop to match the buffer coordinate system, 344 // which means using the inverse of the current transform set on the 345 // SurfaceFlingerConsumer. 346 uint32_t invTransform = mCurrentTransform; 347 if (mSurfaceFlingerConsumer->getTransformToDisplayInverse()) { 348 /* 349 * the code below applies the display's inverse transform to the buffer 350 */ 351 uint32_t invTransformOrient = hw->getOrientationTransform(); 352 // calculate the inverse transform 353 if (invTransformOrient & NATIVE_WINDOW_TRANSFORM_ROT_90) { 354 invTransformOrient ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 355 NATIVE_WINDOW_TRANSFORM_FLIP_H; 356 // If the transform has been rotated the axis of flip has been swapped 357 // so we need to swap which flip operations we are performing 358 bool is_h_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_H) != 0; 359 bool is_v_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_V) != 0; 360 if (is_h_flipped != is_v_flipped) { 361 invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 362 NATIVE_WINDOW_TRANSFORM_FLIP_H; 363 } 364 } 365 // and apply to the current transform 366 invTransform = (Transform(invTransform) * Transform(invTransformOrient)).getOrientation(); 367 } 368 369 int winWidth = s.active.w; 370 int winHeight = s.active.h; 371 if (invTransform & NATIVE_WINDOW_TRANSFORM_ROT_90) { 372 // If the activeCrop has been rotate the ends are rotated but not 373 // the space itself so when transforming ends back we can't rely on 374 // a modification of the axes of rotation. To account for this we 375 // need to reorient the inverse rotation in terms of the current 376 // axes of rotation. 377 bool is_h_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_H) != 0; 378 bool is_v_flipped = (invTransform & NATIVE_WINDOW_TRANSFORM_FLIP_V) != 0; 379 if (is_h_flipped == is_v_flipped) { 380 invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 381 NATIVE_WINDOW_TRANSFORM_FLIP_H; 382 } 383 winWidth = s.active.h; 384 winHeight = s.active.w; 385 } 386 const Rect winCrop = activeCrop.transform( 387 invTransform, s.active.w, s.active.h); 388 389 // below, crop is intersected with winCrop expressed in crop's coordinate space 390 float xScale = crop.getWidth() / float(winWidth); 391 float yScale = crop.getHeight() / float(winHeight); 392 393 float insetL = winCrop.left * xScale; 394 float insetT = winCrop.top * yScale; 395 float insetR = (winWidth - winCrop.right ) * xScale; 396 float insetB = (winHeight - winCrop.bottom) * yScale; 397 398 crop.left += insetL; 399 crop.top += insetT; 400 crop.right -= insetR; 401 crop.bottom -= insetB; 402 } 403 return crop; 404} 405 406void Layer::setGeometry( 407 const sp<const DisplayDevice>& hw, 408 HWComposer::HWCLayerInterface& layer) 409{ 410 layer.setDefaultState(); 411 412 // enable this layer 413 layer.setSkip(false); 414 415 if (isSecure() && !hw->isSecure()) { 416 layer.setSkip(true); 417 } 418 419 // this gives us only the "orientation" component of the transform 420 const State& s(getDrawingState()); 421 if (!isOpaque(s) || s.alpha != 0xFF) { 422 layer.setBlending(mPremultipliedAlpha ? 423 HWC_BLENDING_PREMULT : 424 HWC_BLENDING_COVERAGE); 425 } 426 427 // apply the layer's transform, followed by the display's global transform 428 // here we're guaranteed that the layer's transform preserves rects 429 Region activeTransparentRegion(s.activeTransparentRegion); 430 if (!s.active.crop.isEmpty()) { 431 Rect activeCrop(s.active.crop); 432 activeCrop = s.transform.transform(activeCrop); 433 activeCrop.intersect(hw->getViewport(), &activeCrop); 434 activeCrop = s.transform.inverse().transform(activeCrop); 435 // mark regions outside the crop as transparent 436 activeTransparentRegion.orSelf(Rect(0, 0, s.active.w, activeCrop.top)); 437 activeTransparentRegion.orSelf(Rect(0, activeCrop.bottom, 438 s.active.w, s.active.h)); 439 activeTransparentRegion.orSelf(Rect(0, activeCrop.top, 440 activeCrop.left, activeCrop.bottom)); 441 activeTransparentRegion.orSelf(Rect(activeCrop.right, activeCrop.top, 442 s.active.w, activeCrop.bottom)); 443 } 444 Rect frame(s.transform.transform(computeBounds(activeTransparentRegion))); 445 frame.intersect(hw->getViewport(), &frame); 446 const Transform& tr(hw->getTransform()); 447 layer.setFrame(tr.transform(frame)); 448 layer.setCrop(computeCrop(hw)); 449 layer.setPlaneAlpha(s.alpha); 450 451 /* 452 * Transformations are applied in this order: 453 * 1) buffer orientation/flip/mirror 454 * 2) state transformation (window manager) 455 * 3) layer orientation (screen orientation) 456 * (NOTE: the matrices are multiplied in reverse order) 457 */ 458 459 const Transform bufferOrientation(mCurrentTransform); 460 Transform transform(tr * s.transform * bufferOrientation); 461 462 if (mSurfaceFlingerConsumer->getTransformToDisplayInverse()) { 463 /* 464 * the code below applies the display's inverse transform to the buffer 465 */ 466 uint32_t invTransform = hw->getOrientationTransform(); 467 uint32_t t_orientation = transform.getOrientation(); 468 // calculate the inverse transform 469 if (invTransform & NATIVE_WINDOW_TRANSFORM_ROT_90) { 470 invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 471 NATIVE_WINDOW_TRANSFORM_FLIP_H; 472 // If the transform has been rotated the axis of flip has been swapped 473 // so we need to swap which flip operations we are performing 474 bool is_h_flipped = (t_orientation & NATIVE_WINDOW_TRANSFORM_FLIP_H) != 0; 475 bool is_v_flipped = (t_orientation & NATIVE_WINDOW_TRANSFORM_FLIP_V) != 0; 476 if (is_h_flipped != is_v_flipped) { 477 t_orientation ^= NATIVE_WINDOW_TRANSFORM_FLIP_V | 478 NATIVE_WINDOW_TRANSFORM_FLIP_H; 479 } 480 } 481 // and apply to the current transform 482 transform = Transform(t_orientation) * Transform(invTransform); 483 } 484 485 // this gives us only the "orientation" component of the transform 486 const uint32_t orientation = transform.getOrientation(); 487 if (orientation & Transform::ROT_INVALID) { 488 // we can only handle simple transformation 489 layer.setSkip(true); 490 } else { 491 layer.setTransform(orientation); 492 } 493} 494 495void Layer::setPerFrameData(const sp<const DisplayDevice>& hw, 496 HWComposer::HWCLayerInterface& layer) { 497 // we have to set the visible region on every frame because 498 // we currently free it during onLayerDisplayed(), which is called 499 // after HWComposer::commit() -- every frame. 500 // Apply this display's projection's viewport to the visible region 501 // before giving it to the HWC HAL. 502 const Transform& tr = hw->getTransform(); 503 Region visible = tr.transform(visibleRegion.intersect(hw->getViewport())); 504 layer.setVisibleRegionScreen(visible); 505 506 if (mSidebandStream.get()) { 507 layer.setSidebandStream(mSidebandStream); 508 } else { 509 // NOTE: buffer can be NULL if the client never drew into this 510 // layer yet, or if we ran out of memory 511 layer.setBuffer(mActiveBuffer); 512 } 513} 514 515void Layer::setAcquireFence(const sp<const DisplayDevice>& /* hw */, 516 HWComposer::HWCLayerInterface& layer) { 517 int fenceFd = -1; 518 519 // TODO: there is a possible optimization here: we only need to set the 520 // acquire fence the first time a new buffer is acquired on EACH display. 521 522 if (layer.getCompositionType() == HWC_OVERLAY || layer.getCompositionType() == HWC_CURSOR_OVERLAY) { 523 sp<Fence> fence = mSurfaceFlingerConsumer->getCurrentFence(); 524 if (fence->isValid()) { 525 fenceFd = fence->dup(); 526 if (fenceFd == -1) { 527 ALOGW("failed to dup layer fence, skipping sync: %d", errno); 528 } 529 } 530 } 531 layer.setAcquireFenceFd(fenceFd); 532} 533 534Rect Layer::getPosition( 535 const sp<const DisplayDevice>& hw) 536{ 537 // this gives us only the "orientation" component of the transform 538 const State& s(getCurrentState()); 539 540 // apply the layer's transform, followed by the display's global transform 541 // here we're guaranteed that the layer's transform preserves rects 542 Rect win(s.active.w, s.active.h); 543 if (!s.active.crop.isEmpty()) { 544 win.intersect(s.active.crop, &win); 545 } 546 // subtract the transparent region and snap to the bounds 547 Rect bounds = reduce(win, s.activeTransparentRegion); 548 Rect frame(s.transform.transform(bounds)); 549 frame.intersect(hw->getViewport(), &frame); 550 const Transform& tr(hw->getTransform()); 551 return Rect(tr.transform(frame)); 552} 553 554// --------------------------------------------------------------------------- 555// drawing... 556// --------------------------------------------------------------------------- 557 558void Layer::draw(const sp<const DisplayDevice>& hw, const Region& clip) const { 559 onDraw(hw, clip, false); 560} 561 562void Layer::draw(const sp<const DisplayDevice>& hw, 563 bool useIdentityTransform) const { 564 onDraw(hw, Region(hw->bounds()), useIdentityTransform); 565} 566 567void Layer::draw(const sp<const DisplayDevice>& hw) const { 568 onDraw(hw, Region(hw->bounds()), false); 569} 570 571void Layer::onDraw(const sp<const DisplayDevice>& hw, const Region& clip, 572 bool useIdentityTransform) const 573{ 574 ATRACE_CALL(); 575 576 if (CC_UNLIKELY(mActiveBuffer == 0)) { 577 // the texture has not been created yet, this Layer has 578 // in fact never been drawn into. This happens frequently with 579 // SurfaceView because the WindowManager can't know when the client 580 // has drawn the first time. 581 582 // If there is nothing under us, we paint the screen in black, otherwise 583 // we just skip this update. 584 585 // figure out if there is something below us 586 Region under; 587 const SurfaceFlinger::LayerVector& drawingLayers( 588 mFlinger->mDrawingState.layersSortedByZ); 589 const size_t count = drawingLayers.size(); 590 for (size_t i=0 ; i<count ; ++i) { 591 const sp<Layer>& layer(drawingLayers[i]); 592 if (layer.get() == static_cast<Layer const*>(this)) 593 break; 594 under.orSelf( hw->getTransform().transform(layer->visibleRegion) ); 595 } 596 // if not everything below us is covered, we plug the holes! 597 Region holes(clip.subtract(under)); 598 if (!holes.isEmpty()) { 599 clearWithOpenGL(hw, holes, 0, 0, 0, 1); 600 } 601 return; 602 } 603 604 // Bind the current buffer to the GL texture, and wait for it to be 605 // ready for us to draw into. 606 status_t err = mSurfaceFlingerConsumer->bindTextureImage(); 607 if (err != NO_ERROR) { 608 ALOGW("onDraw: bindTextureImage failed (err=%d)", err); 609 // Go ahead and draw the buffer anyway; no matter what we do the screen 610 // is probably going to have something visibly wrong. 611 } 612 613 bool blackOutLayer = isProtected() || (isSecure() && !hw->isSecure()); 614 615 RenderEngine& engine(mFlinger->getRenderEngine()); 616 617 if (!blackOutLayer) { 618 // TODO: we could be more subtle with isFixedSize() 619 const bool useFiltering = getFiltering() || needsFiltering(hw) || isFixedSize(); 620 621 // Query the texture matrix given our current filtering mode. 622 float textureMatrix[16]; 623 mSurfaceFlingerConsumer->setFilteringEnabled(useFiltering); 624 mSurfaceFlingerConsumer->getTransformMatrix(textureMatrix); 625 626 if (mSurfaceFlingerConsumer->getTransformToDisplayInverse()) { 627 628 /* 629 * the code below applies the display's inverse transform to the texture transform 630 */ 631 632 // create a 4x4 transform matrix from the display transform flags 633 const mat4 flipH(-1,0,0,0, 0,1,0,0, 0,0,1,0, 1,0,0,1); 634 const mat4 flipV( 1,0,0,0, 0,-1,0,0, 0,0,1,0, 0,1,0,1); 635 const mat4 rot90( 0,1,0,0, -1,0,0,0, 0,0,1,0, 1,0,0,1); 636 637 mat4 tr; 638 uint32_t transform = hw->getOrientationTransform(); 639 if (transform & NATIVE_WINDOW_TRANSFORM_ROT_90) 640 tr = tr * rot90; 641 if (transform & NATIVE_WINDOW_TRANSFORM_FLIP_H) 642 tr = tr * flipH; 643 if (transform & NATIVE_WINDOW_TRANSFORM_FLIP_V) 644 tr = tr * flipV; 645 646 // calculate the inverse 647 tr = inverse(tr); 648 649 // and finally apply it to the original texture matrix 650 const mat4 texTransform(mat4(static_cast<const float*>(textureMatrix)) * tr); 651 memcpy(textureMatrix, texTransform.asArray(), sizeof(textureMatrix)); 652 } 653 654 // Set things up for texturing. 655 mTexture.setDimensions(mActiveBuffer->getWidth(), mActiveBuffer->getHeight()); 656 mTexture.setFiltering(useFiltering); 657 mTexture.setMatrix(textureMatrix); 658 659 engine.setupLayerTexturing(mTexture); 660 } else { 661 engine.setupLayerBlackedOut(); 662 } 663 drawWithOpenGL(hw, clip, useIdentityTransform); 664 engine.disableTexturing(); 665} 666 667 668void Layer::clearWithOpenGL(const sp<const DisplayDevice>& hw, 669 const Region& /* clip */, float red, float green, float blue, 670 float alpha) const 671{ 672 RenderEngine& engine(mFlinger->getRenderEngine()); 673 computeGeometry(hw, mMesh, false); 674 engine.setupFillWithColor(red, green, blue, alpha); 675 engine.drawMesh(mMesh); 676} 677 678void Layer::clearWithOpenGL( 679 const sp<const DisplayDevice>& hw, const Region& clip) const { 680 clearWithOpenGL(hw, clip, 0,0,0,0); 681} 682 683void Layer::drawWithOpenGL(const sp<const DisplayDevice>& hw, 684 const Region& /* clip */, bool useIdentityTransform) const { 685 const uint32_t fbHeight = hw->getHeight(); 686 const State& s(getDrawingState()); 687 688 computeGeometry(hw, mMesh, useIdentityTransform); 689 690 /* 691 * NOTE: the way we compute the texture coordinates here produces 692 * different results than when we take the HWC path -- in the later case 693 * the "source crop" is rounded to texel boundaries. 694 * This can produce significantly different results when the texture 695 * is scaled by a large amount. 696 * 697 * The GL code below is more logical (imho), and the difference with 698 * HWC is due to a limitation of the HWC API to integers -- a question 699 * is suspend is whether we should ignore this problem or revert to 700 * GL composition when a buffer scaling is applied (maybe with some 701 * minimal value)? Or, we could make GL behave like HWC -- but this feel 702 * like more of a hack. 703 */ 704 const Rect win(computeBounds()); 705 706 float left = float(win.left) / float(s.active.w); 707 float top = float(win.top) / float(s.active.h); 708 float right = float(win.right) / float(s.active.w); 709 float bottom = float(win.bottom) / float(s.active.h); 710 711 // TODO: we probably want to generate the texture coords with the mesh 712 // here we assume that we only have 4 vertices 713 Mesh::VertexArray<vec2> texCoords(mMesh.getTexCoordArray<vec2>()); 714 texCoords[0] = vec2(left, 1.0f - top); 715 texCoords[1] = vec2(left, 1.0f - bottom); 716 texCoords[2] = vec2(right, 1.0f - bottom); 717 texCoords[3] = vec2(right, 1.0f - top); 718 719 RenderEngine& engine(mFlinger->getRenderEngine()); 720 engine.setupLayerBlending(mPremultipliedAlpha, isOpaque(s), s.alpha); 721 engine.drawMesh(mMesh); 722 engine.disableBlending(); 723} 724 725uint32_t Layer::getProducerStickyTransform() const { 726 int producerStickyTransform = 0; 727 int ret = mProducer->query(NATIVE_WINDOW_STICKY_TRANSFORM, &producerStickyTransform); 728 if (ret != OK) { 729 ALOGW("%s: Error %s (%d) while querying window sticky transform.", __FUNCTION__, 730 strerror(-ret), ret); 731 return 0; 732 } 733 return static_cast<uint32_t>(producerStickyTransform); 734} 735 736void Layer::setFiltering(bool filtering) { 737 mFiltering = filtering; 738} 739 740bool Layer::getFiltering() const { 741 return mFiltering; 742} 743 744// As documented in libhardware header, formats in the range 745// 0x100 - 0x1FF are specific to the HAL implementation, and 746// are known to have no alpha channel 747// TODO: move definition for device-specific range into 748// hardware.h, instead of using hard-coded values here. 749#define HARDWARE_IS_DEVICE_FORMAT(f) ((f) >= 0x100 && (f) <= 0x1FF) 750 751bool Layer::getOpacityForFormat(uint32_t format) { 752 if (HARDWARE_IS_DEVICE_FORMAT(format)) { 753 return true; 754 } 755 switch (format) { 756 case HAL_PIXEL_FORMAT_RGBA_8888: 757 case HAL_PIXEL_FORMAT_BGRA_8888: 758 case HAL_PIXEL_FORMAT_sRGB_A_8888: 759 return false; 760 } 761 // in all other case, we have no blending (also for unknown formats) 762 return true; 763} 764 765// ---------------------------------------------------------------------------- 766// local state 767// ---------------------------------------------------------------------------- 768 769void Layer::computeGeometry(const sp<const DisplayDevice>& hw, Mesh& mesh, 770 bool useIdentityTransform) const 771{ 772 const Layer::State& s(getDrawingState()); 773 const Transform tr(useIdentityTransform ? 774 hw->getTransform() : hw->getTransform() * s.transform); 775 const uint32_t hw_h = hw->getHeight(); 776 Rect win(s.active.w, s.active.h); 777 if (!s.active.crop.isEmpty()) { 778 win.intersect(s.active.crop, &win); 779 } 780 // subtract the transparent region and snap to the bounds 781 win = reduce(win, s.activeTransparentRegion); 782 783 Mesh::VertexArray<vec2> position(mesh.getPositionArray<vec2>()); 784 position[0] = tr.transform(win.left, win.top); 785 position[1] = tr.transform(win.left, win.bottom); 786 position[2] = tr.transform(win.right, win.bottom); 787 position[3] = tr.transform(win.right, win.top); 788 for (size_t i=0 ; i<4 ; i++) { 789 position[i].y = hw_h - position[i].y; 790 } 791} 792 793bool Layer::isOpaque(const Layer::State& s) const 794{ 795 // if we don't have a buffer yet, we're translucent regardless of the 796 // layer's opaque flag. 797 if (mActiveBuffer == 0) { 798 return false; 799 } 800 801 // if the layer has the opaque flag, then we're always opaque, 802 // otherwise we use the current buffer's format. 803 return ((s.flags & layer_state_t::eLayerOpaque) != 0) || mCurrentOpacity; 804} 805 806bool Layer::isProtected() const 807{ 808 const sp<GraphicBuffer>& activeBuffer(mActiveBuffer); 809 return (activeBuffer != 0) && 810 (activeBuffer->getUsage() & GRALLOC_USAGE_PROTECTED); 811} 812 813bool Layer::isFixedSize() const { 814 return mCurrentScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE; 815} 816 817bool Layer::isCropped() const { 818 return !mCurrentCrop.isEmpty(); 819} 820 821bool Layer::needsFiltering(const sp<const DisplayDevice>& hw) const { 822 return mNeedsFiltering || hw->needsFiltering(); 823} 824 825void Layer::setVisibleRegion(const Region& visibleRegion) { 826 // always called from main thread 827 this->visibleRegion = visibleRegion; 828} 829 830void Layer::setCoveredRegion(const Region& coveredRegion) { 831 // always called from main thread 832 this->coveredRegion = coveredRegion; 833} 834 835void Layer::setVisibleNonTransparentRegion(const Region& 836 setVisibleNonTransparentRegion) { 837 // always called from main thread 838 this->visibleNonTransparentRegion = setVisibleNonTransparentRegion; 839} 840 841// ---------------------------------------------------------------------------- 842// transaction 843// ---------------------------------------------------------------------------- 844 845uint32_t Layer::doTransaction(uint32_t flags) { 846 ATRACE_CALL(); 847 848 const Layer::State& s(getDrawingState()); 849 const Layer::State& c(getCurrentState()); 850 851 const bool sizeChanged = (c.requested.w != s.requested.w) || 852 (c.requested.h != s.requested.h); 853 854 if (sizeChanged) { 855 // the size changed, we need to ask our client to request a new buffer 856 ALOGD_IF(DEBUG_RESIZE, 857 "doTransaction: geometry (layer=%p '%s'), tr=%02x, scalingMode=%d\n" 858 " current={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n" 859 " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n" 860 " drawing={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n" 861 " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n", 862 this, getName().string(), mCurrentTransform, mCurrentScalingMode, 863 c.active.w, c.active.h, 864 c.active.crop.left, 865 c.active.crop.top, 866 c.active.crop.right, 867 c.active.crop.bottom, 868 c.active.crop.getWidth(), 869 c.active.crop.getHeight(), 870 c.requested.w, c.requested.h, 871 c.requested.crop.left, 872 c.requested.crop.top, 873 c.requested.crop.right, 874 c.requested.crop.bottom, 875 c.requested.crop.getWidth(), 876 c.requested.crop.getHeight(), 877 s.active.w, s.active.h, 878 s.active.crop.left, 879 s.active.crop.top, 880 s.active.crop.right, 881 s.active.crop.bottom, 882 s.active.crop.getWidth(), 883 s.active.crop.getHeight(), 884 s.requested.w, s.requested.h, 885 s.requested.crop.left, 886 s.requested.crop.top, 887 s.requested.crop.right, 888 s.requested.crop.bottom, 889 s.requested.crop.getWidth(), 890 s.requested.crop.getHeight()); 891 892 // record the new size, form this point on, when the client request 893 // a buffer, it'll get the new size. 894 mSurfaceFlingerConsumer->setDefaultBufferSize( 895 c.requested.w, c.requested.h); 896 } 897 898 if (!isFixedSize()) { 899 900 const bool resizePending = (c.requested.w != c.active.w) || 901 (c.requested.h != c.active.h); 902 903 if (resizePending) { 904 // don't let Layer::doTransaction update the drawing state 905 // if we have a pending resize, unless we are in fixed-size mode. 906 // the drawing state will be updated only once we receive a buffer 907 // with the correct size. 908 // 909 // in particular, we want to make sure the clip (which is part 910 // of the geometry state) is latched together with the size but is 911 // latched immediately when no resizing is involved. 912 913 flags |= eDontUpdateGeometryState; 914 } 915 } 916 917 // always set active to requested, unless we're asked not to 918 // this is used by Layer, which special cases resizes. 919 if (flags & eDontUpdateGeometryState) { 920 } else { 921 Layer::State& editCurrentState(getCurrentState()); 922 editCurrentState.active = c.requested; 923 } 924 925 if (s.active != c.active) { 926 // invalidate and recompute the visible regions if needed 927 flags |= Layer::eVisibleRegion; 928 } 929 930 if (c.sequence != s.sequence) { 931 // invalidate and recompute the visible regions if needed 932 flags |= eVisibleRegion; 933 this->contentDirty = true; 934 935 // we may use linear filtering, if the matrix scales us 936 const uint8_t type = c.transform.getType(); 937 mNeedsFiltering = (!c.transform.preserveRects() || 938 (type >= Transform::SCALE)); 939 } 940 941 // Commit the transaction 942 commitTransaction(); 943 return flags; 944} 945 946void Layer::commitTransaction() { 947 mDrawingState = mCurrentState; 948} 949 950uint32_t Layer::getTransactionFlags(uint32_t flags) { 951 return android_atomic_and(~flags, &mTransactionFlags) & flags; 952} 953 954uint32_t Layer::setTransactionFlags(uint32_t flags) { 955 return android_atomic_or(flags, &mTransactionFlags); 956} 957 958bool Layer::setPosition(float x, float y) { 959 if (mCurrentState.transform.tx() == x && mCurrentState.transform.ty() == y) 960 return false; 961 mCurrentState.sequence++; 962 mCurrentState.transform.set(x, y); 963 setTransactionFlags(eTransactionNeeded); 964 return true; 965} 966bool Layer::setLayer(uint32_t z) { 967 if (mCurrentState.z == z) 968 return false; 969 mCurrentState.sequence++; 970 mCurrentState.z = z; 971 setTransactionFlags(eTransactionNeeded); 972 return true; 973} 974bool Layer::setSize(uint32_t w, uint32_t h) { 975 if (mCurrentState.requested.w == w && mCurrentState.requested.h == h) 976 return false; 977 mCurrentState.requested.w = w; 978 mCurrentState.requested.h = h; 979 setTransactionFlags(eTransactionNeeded); 980 return true; 981} 982bool Layer::setAlpha(uint8_t alpha) { 983 if (mCurrentState.alpha == alpha) 984 return false; 985 mCurrentState.sequence++; 986 mCurrentState.alpha = alpha; 987 setTransactionFlags(eTransactionNeeded); 988 return true; 989} 990bool Layer::setMatrix(const layer_state_t::matrix22_t& matrix) { 991 mCurrentState.sequence++; 992 mCurrentState.transform.set( 993 matrix.dsdx, matrix.dsdy, matrix.dtdx, matrix.dtdy); 994 setTransactionFlags(eTransactionNeeded); 995 return true; 996} 997bool Layer::setTransparentRegionHint(const Region& transparent) { 998 mCurrentState.requestedTransparentRegion = transparent; 999 setTransactionFlags(eTransactionNeeded); 1000 return true; 1001} 1002bool Layer::setFlags(uint8_t flags, uint8_t mask) { 1003 const uint32_t newFlags = (mCurrentState.flags & ~mask) | (flags & mask); 1004 if (mCurrentState.flags == newFlags) 1005 return false; 1006 mCurrentState.sequence++; 1007 mCurrentState.flags = newFlags; 1008 setTransactionFlags(eTransactionNeeded); 1009 return true; 1010} 1011bool Layer::setCrop(const Rect& crop) { 1012 if (mCurrentState.requested.crop == crop) 1013 return false; 1014 mCurrentState.sequence++; 1015 mCurrentState.requested.crop = crop; 1016 setTransactionFlags(eTransactionNeeded); 1017 return true; 1018} 1019 1020bool Layer::setLayerStack(uint32_t layerStack) { 1021 if (mCurrentState.layerStack == layerStack) 1022 return false; 1023 mCurrentState.sequence++; 1024 mCurrentState.layerStack = layerStack; 1025 setTransactionFlags(eTransactionNeeded); 1026 return true; 1027} 1028 1029// ---------------------------------------------------------------------------- 1030// pageflip handling... 1031// ---------------------------------------------------------------------------- 1032 1033bool Layer::shouldPresentNow(const DispSync& dispSync) const { 1034 Mutex::Autolock lock(mQueueItemLock); 1035 nsecs_t expectedPresent = 1036 mSurfaceFlingerConsumer->computeExpectedPresent(dispSync); 1037 return mQueueItems.empty() ? 1038 false : mQueueItems[0].mTimestamp < expectedPresent; 1039} 1040 1041bool Layer::onPreComposition() { 1042 mRefreshPending = false; 1043 return mQueuedFrames > 0 || mSidebandStreamChanged; 1044} 1045 1046void Layer::onPostComposition() { 1047 if (mFrameLatencyNeeded) { 1048 nsecs_t desiredPresentTime = mSurfaceFlingerConsumer->getTimestamp(); 1049 mFrameTracker.setDesiredPresentTime(desiredPresentTime); 1050 1051 sp<Fence> frameReadyFence = mSurfaceFlingerConsumer->getCurrentFence(); 1052 if (frameReadyFence->isValid()) { 1053 mFrameTracker.setFrameReadyFence(frameReadyFence); 1054 } else { 1055 // There was no fence for this frame, so assume that it was ready 1056 // to be presented at the desired present time. 1057 mFrameTracker.setFrameReadyTime(desiredPresentTime); 1058 } 1059 1060 const HWComposer& hwc = mFlinger->getHwComposer(); 1061 sp<Fence> presentFence = hwc.getDisplayFence(HWC_DISPLAY_PRIMARY); 1062 if (presentFence->isValid()) { 1063 mFrameTracker.setActualPresentFence(presentFence); 1064 } else { 1065 // The HWC doesn't support present fences, so use the refresh 1066 // timestamp instead. 1067 nsecs_t presentTime = hwc.getRefreshTimestamp(HWC_DISPLAY_PRIMARY); 1068 mFrameTracker.setActualPresentTime(presentTime); 1069 } 1070 1071 mFrameTracker.advanceFrame(); 1072 mFrameLatencyNeeded = false; 1073 } 1074} 1075 1076bool Layer::isVisible() const { 1077 const Layer::State& s(mDrawingState); 1078 return !(s.flags & layer_state_t::eLayerHidden) && s.alpha 1079 && (mActiveBuffer != NULL || mSidebandStream != NULL); 1080} 1081 1082Region Layer::latchBuffer(bool& recomputeVisibleRegions) 1083{ 1084 ATRACE_CALL(); 1085 1086 if (android_atomic_acquire_cas(true, false, &mSidebandStreamChanged) == 0) { 1087 // mSidebandStreamChanged was true 1088 mSidebandStream = mSurfaceFlingerConsumer->getSidebandStream(); 1089 recomputeVisibleRegions = true; 1090 1091 const State& s(getDrawingState()); 1092 return s.transform.transform(Region(Rect(s.active.w, s.active.h))); 1093 } 1094 1095 Region outDirtyRegion; 1096 if (mQueuedFrames > 0) { 1097 1098 // if we've already called updateTexImage() without going through 1099 // a composition step, we have to skip this layer at this point 1100 // because we cannot call updateTeximage() without a corresponding 1101 // compositionComplete() call. 1102 // we'll trigger an update in onPreComposition(). 1103 if (mRefreshPending) { 1104 return outDirtyRegion; 1105 } 1106 1107 // Capture the old state of the layer for comparisons later 1108 const State& s(getDrawingState()); 1109 const bool oldOpacity = isOpaque(s); 1110 sp<GraphicBuffer> oldActiveBuffer = mActiveBuffer; 1111 1112 struct Reject : public SurfaceFlingerConsumer::BufferRejecter { 1113 Layer::State& front; 1114 Layer::State& current; 1115 bool& recomputeVisibleRegions; 1116 bool stickyTransformSet; 1117 Reject(Layer::State& front, Layer::State& current, 1118 bool& recomputeVisibleRegions, bool stickySet) 1119 : front(front), current(current), 1120 recomputeVisibleRegions(recomputeVisibleRegions), 1121 stickyTransformSet(stickySet) { 1122 } 1123 1124 virtual bool reject(const sp<GraphicBuffer>& buf, 1125 const IGraphicBufferConsumer::BufferItem& item) { 1126 if (buf == NULL) { 1127 return false; 1128 } 1129 1130 uint32_t bufWidth = buf->getWidth(); 1131 uint32_t bufHeight = buf->getHeight(); 1132 1133 // check that we received a buffer of the right size 1134 // (Take the buffer's orientation into account) 1135 if (item.mTransform & Transform::ROT_90) { 1136 swap(bufWidth, bufHeight); 1137 } 1138 1139 bool isFixedSize = item.mScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE; 1140 if (front.active != front.requested) { 1141 1142 if (isFixedSize || 1143 (bufWidth == front.requested.w && 1144 bufHeight == front.requested.h)) 1145 { 1146 // Here we pretend the transaction happened by updating the 1147 // current and drawing states. Drawing state is only accessed 1148 // in this thread, no need to have it locked 1149 front.active = front.requested; 1150 1151 // We also need to update the current state so that 1152 // we don't end-up overwriting the drawing state with 1153 // this stale current state during the next transaction 1154 // 1155 // NOTE: We don't need to hold the transaction lock here 1156 // because State::active is only accessed from this thread. 1157 current.active = front.active; 1158 1159 // recompute visible region 1160 recomputeVisibleRegions = true; 1161 } 1162 1163 ALOGD_IF(DEBUG_RESIZE, 1164 "latchBuffer/reject: buffer (%ux%u, tr=%02x), scalingMode=%d\n" 1165 " drawing={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n" 1166 " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n", 1167 bufWidth, bufHeight, item.mTransform, item.mScalingMode, 1168 front.active.w, front.active.h, 1169 front.active.crop.left, 1170 front.active.crop.top, 1171 front.active.crop.right, 1172 front.active.crop.bottom, 1173 front.active.crop.getWidth(), 1174 front.active.crop.getHeight(), 1175 front.requested.w, front.requested.h, 1176 front.requested.crop.left, 1177 front.requested.crop.top, 1178 front.requested.crop.right, 1179 front.requested.crop.bottom, 1180 front.requested.crop.getWidth(), 1181 front.requested.crop.getHeight()); 1182 } 1183 1184 if (!isFixedSize && !stickyTransformSet) { 1185 if (front.active.w != bufWidth || 1186 front.active.h != bufHeight) { 1187 // reject this buffer 1188 ALOGE("rejecting buffer: bufWidth=%d, bufHeight=%d, front.active.{w=%d, h=%d}", 1189 bufWidth, bufHeight, front.active.w, front.active.h); 1190 return true; 1191 } 1192 } 1193 1194 // if the transparent region has changed (this test is 1195 // conservative, but that's fine, worst case we're doing 1196 // a bit of extra work), we latch the new one and we 1197 // trigger a visible-region recompute. 1198 if (!front.activeTransparentRegion.isTriviallyEqual( 1199 front.requestedTransparentRegion)) { 1200 front.activeTransparentRegion = front.requestedTransparentRegion; 1201 1202 // We also need to update the current state so that 1203 // we don't end-up overwriting the drawing state with 1204 // this stale current state during the next transaction 1205 // 1206 // NOTE: We don't need to hold the transaction lock here 1207 // because State::active is only accessed from this thread. 1208 current.activeTransparentRegion = front.activeTransparentRegion; 1209 1210 // recompute visible region 1211 recomputeVisibleRegions = true; 1212 } 1213 1214 return false; 1215 } 1216 }; 1217 1218 Reject r(mDrawingState, getCurrentState(), recomputeVisibleRegions, 1219 getProducerStickyTransform() != 0); 1220 1221 status_t updateResult = mSurfaceFlingerConsumer->updateTexImage(&r, 1222 mFlinger->mPrimaryDispSync); 1223 if (updateResult == BufferQueue::PRESENT_LATER) { 1224 // Producer doesn't want buffer to be displayed yet. Signal a 1225 // layer update so we check again at the next opportunity. 1226 mFlinger->signalLayerUpdate(); 1227 return outDirtyRegion; 1228 } 1229 1230 // Remove this buffer from our internal queue tracker 1231 { // Autolock scope 1232 Mutex::Autolock lock(mQueueItemLock); 1233 mQueueItems.removeAt(0); 1234 } 1235 1236 // Decrement the queued-frames count. Signal another event if we 1237 // have more frames pending. 1238 if (android_atomic_dec(&mQueuedFrames) > 1) { 1239 mFlinger->signalLayerUpdate(); 1240 } 1241 1242 if (updateResult != NO_ERROR) { 1243 // something happened! 1244 recomputeVisibleRegions = true; 1245 return outDirtyRegion; 1246 } 1247 1248 // update the active buffer 1249 mActiveBuffer = mSurfaceFlingerConsumer->getCurrentBuffer(); 1250 if (mActiveBuffer == NULL) { 1251 // this can only happen if the very first buffer was rejected. 1252 return outDirtyRegion; 1253 } 1254 1255 mRefreshPending = true; 1256 mFrameLatencyNeeded = true; 1257 if (oldActiveBuffer == NULL) { 1258 // the first time we receive a buffer, we need to trigger a 1259 // geometry invalidation. 1260 recomputeVisibleRegions = true; 1261 } 1262 1263 Rect crop(mSurfaceFlingerConsumer->getCurrentCrop()); 1264 const uint32_t transform(mSurfaceFlingerConsumer->getCurrentTransform()); 1265 const uint32_t scalingMode(mSurfaceFlingerConsumer->getCurrentScalingMode()); 1266 if ((crop != mCurrentCrop) || 1267 (transform != mCurrentTransform) || 1268 (scalingMode != mCurrentScalingMode)) 1269 { 1270 mCurrentCrop = crop; 1271 mCurrentTransform = transform; 1272 mCurrentScalingMode = scalingMode; 1273 recomputeVisibleRegions = true; 1274 } 1275 1276 if (oldActiveBuffer != NULL) { 1277 uint32_t bufWidth = mActiveBuffer->getWidth(); 1278 uint32_t bufHeight = mActiveBuffer->getHeight(); 1279 if (bufWidth != uint32_t(oldActiveBuffer->width) || 1280 bufHeight != uint32_t(oldActiveBuffer->height)) { 1281 recomputeVisibleRegions = true; 1282 } 1283 } 1284 1285 mCurrentOpacity = getOpacityForFormat(mActiveBuffer->format); 1286 if (oldOpacity != isOpaque(s)) { 1287 recomputeVisibleRegions = true; 1288 } 1289 1290 // FIXME: postedRegion should be dirty & bounds 1291 Region dirtyRegion(Rect(s.active.w, s.active.h)); 1292 1293 // transform the dirty region to window-manager space 1294 outDirtyRegion = (s.transform.transform(dirtyRegion)); 1295 } 1296 return outDirtyRegion; 1297} 1298 1299uint32_t Layer::getEffectiveUsage(uint32_t usage) const 1300{ 1301 // TODO: should we do something special if mSecure is set? 1302 if (mProtectedByApp) { 1303 // need a hardware-protected path to external video sink 1304 usage |= GraphicBuffer::USAGE_PROTECTED; 1305 } 1306 if (mPotentialCursor) { 1307 usage |= GraphicBuffer::USAGE_CURSOR; 1308 } 1309 usage |= GraphicBuffer::USAGE_HW_COMPOSER; 1310 return usage; 1311} 1312 1313void Layer::updateTransformHint(const sp<const DisplayDevice>& hw) const { 1314 uint32_t orientation = 0; 1315 if (!mFlinger->mDebugDisableTransformHint) { 1316 // The transform hint is used to improve performance, but we can 1317 // only have a single transform hint, it cannot 1318 // apply to all displays. 1319 const Transform& planeTransform(hw->getTransform()); 1320 orientation = planeTransform.getOrientation(); 1321 if (orientation & Transform::ROT_INVALID) { 1322 orientation = 0; 1323 } 1324 } 1325 mSurfaceFlingerConsumer->setTransformHint(orientation); 1326} 1327 1328// ---------------------------------------------------------------------------- 1329// debugging 1330// ---------------------------------------------------------------------------- 1331 1332void Layer::dump(String8& result, Colorizer& colorizer) const 1333{ 1334 const Layer::State& s(getDrawingState()); 1335 1336 colorizer.colorize(result, Colorizer::GREEN); 1337 result.appendFormat( 1338 "+ %s %p (%s)\n", 1339 getTypeId(), this, getName().string()); 1340 colorizer.reset(result); 1341 1342 s.activeTransparentRegion.dump(result, "transparentRegion"); 1343 visibleRegion.dump(result, "visibleRegion"); 1344 sp<Client> client(mClientRef.promote()); 1345 1346 result.appendFormat( " " 1347 "layerStack=%4d, z=%9d, pos=(%g,%g), size=(%4d,%4d), crop=(%4d,%4d,%4d,%4d), " 1348 "isOpaque=%1d, invalidate=%1d, " 1349 "alpha=0x%02x, flags=0x%08x, tr=[%.2f, %.2f][%.2f, %.2f]\n" 1350 " client=%p\n", 1351 s.layerStack, s.z, s.transform.tx(), s.transform.ty(), s.active.w, s.active.h, 1352 s.active.crop.left, s.active.crop.top, 1353 s.active.crop.right, s.active.crop.bottom, 1354 isOpaque(s), contentDirty, 1355 s.alpha, s.flags, 1356 s.transform[0][0], s.transform[0][1], 1357 s.transform[1][0], s.transform[1][1], 1358 client.get()); 1359 1360 sp<const GraphicBuffer> buf0(mActiveBuffer); 1361 uint32_t w0=0, h0=0, s0=0, f0=0; 1362 if (buf0 != 0) { 1363 w0 = buf0->getWidth(); 1364 h0 = buf0->getHeight(); 1365 s0 = buf0->getStride(); 1366 f0 = buf0->format; 1367 } 1368 result.appendFormat( 1369 " " 1370 "format=%2d, activeBuffer=[%4ux%4u:%4u,%3X]," 1371 " queued-frames=%d, mRefreshPending=%d\n", 1372 mFormat, w0, h0, s0,f0, 1373 mQueuedFrames, mRefreshPending); 1374 1375 if (mSurfaceFlingerConsumer != 0) { 1376 mSurfaceFlingerConsumer->dump(result, " "); 1377 } 1378} 1379 1380void Layer::dumpFrameStats(String8& result) const { 1381 mFrameTracker.dumpStats(result); 1382} 1383 1384void Layer::clearFrameStats() { 1385 mFrameTracker.clearStats(); 1386} 1387 1388void Layer::logFrameStats() { 1389 mFrameTracker.logAndResetStats(mName); 1390} 1391 1392void Layer::getFrameStats(FrameStats* outStats) const { 1393 mFrameTracker.getStats(outStats); 1394} 1395 1396// --------------------------------------------------------------------------- 1397 1398Layer::LayerCleaner::LayerCleaner(const sp<SurfaceFlinger>& flinger, 1399 const sp<Layer>& layer) 1400 : mFlinger(flinger), mLayer(layer) { 1401} 1402 1403Layer::LayerCleaner::~LayerCleaner() { 1404 // destroy client resources 1405 mFlinger->onLayerDestroyed(mLayer); 1406} 1407 1408// --------------------------------------------------------------------------- 1409}; // namespace android 1410 1411#if defined(__gl_h_) 1412#error "don't include gl/gl.h in this file" 1413#endif 1414 1415#if defined(__gl2_h_) 1416#error "don't include gl2/gl2.h in this file" 1417#endif 1418