Layer.cpp revision 99ce5cdeb383216dee95af4d90e47406b0948ea1
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#include <stdlib.h> 18#include <stdint.h> 19#include <sys/types.h> 20 21#include <cutils/compiler.h> 22#include <cutils/native_handle.h> 23#include <cutils/properties.h> 24 25#include <utils/Errors.h> 26#include <utils/Log.h> 27#include <utils/StopWatch.h> 28 29#include <ui/GraphicBuffer.h> 30#include <ui/PixelFormat.h> 31 32#include <surfaceflinger/Surface.h> 33 34#include "clz.h" 35#include "DisplayHardware/DisplayHardware.h" 36#include "DisplayHardware/HWComposer.h" 37#include "GLExtensions.h" 38#include "Layer.h" 39#include "SurfaceFlinger.h" 40#include "SurfaceTextureLayer.h" 41#include <math.h> 42 43#define DEBUG_RESIZE 0 44 45 46namespace android { 47 48// --------------------------------------------------------------------------- 49 50Layer::Layer(SurfaceFlinger* flinger, 51 DisplayID display, const sp<Client>& client) 52 : LayerBaseClient(flinger, display, client), 53 mTextureName(-1U), 54 mQueuedFrames(0), 55 mCurrentTransform(0), 56 mCurrentScalingMode(NATIVE_WINDOW_SCALING_MODE_FREEZE), 57 mCurrentOpacity(true), 58 mRefreshPending(0), 59 mFrameLatencyNeeded(false), 60 mFrameLatencyOffset(0), 61 mFormat(PIXEL_FORMAT_NONE), 62 mGLExtensions(GLExtensions::getInstance()), 63 mOpaqueLayer(true), 64 mNeedsDithering(false), 65 mSecure(false), 66 mProtectedByApp(false) 67{ 68 mCurrentCrop.makeInvalid(); 69 glGenTextures(1, &mTextureName); 70} 71 72void Layer::onLayerDisplayed() { 73 if (mFrameLatencyNeeded) { 74 const DisplayHardware& hw(graphicPlane(0).displayHardware()); 75 mFrameStats[mFrameLatencyOffset].timestamp = mSurfaceTexture->getTimestamp(); 76 mFrameStats[mFrameLatencyOffset].set = systemTime(); 77 mFrameStats[mFrameLatencyOffset].vsync = hw.getRefreshTimestamp(); 78 mFrameLatencyOffset = (mFrameLatencyOffset + 1) % 128; 79 mFrameLatencyNeeded = false; 80 } 81} 82 83void Layer::onFirstRef() 84{ 85 LayerBaseClient::onFirstRef(); 86 87 struct FrameQueuedListener : public SurfaceTexture::FrameAvailableListener { 88 FrameQueuedListener(Layer* layer) : mLayer(layer) { } 89 private: 90 wp<Layer> mLayer; 91 virtual void onFrameAvailable() { 92 sp<Layer> that(mLayer.promote()); 93 if (that != 0) { 94 that->onFrameQueued(); 95 } 96 } 97 }; 98 mSurfaceTexture = new SurfaceTextureLayer(mTextureName, this); 99 mSurfaceTexture->setFrameAvailableListener(new FrameQueuedListener(this)); 100 mSurfaceTexture->setSynchronousMode(true); 101 mSurfaceTexture->setBufferCountServer(2); 102} 103 104Layer::~Layer() 105{ 106 mFlinger->postMessageAsync( 107 new SurfaceFlinger::MessageDestroyGLTexture(mTextureName) ); 108} 109 110void Layer::onFrameQueued() { 111 android_atomic_inc(&mQueuedFrames); 112 mFlinger->signalLayerUpdate(); 113} 114 115// called with SurfaceFlinger::mStateLock as soon as the layer is entered 116// in the purgatory list 117void Layer::onRemoved() 118{ 119 mSurfaceTexture->abandon(); 120} 121 122void Layer::setName(const String8& name) { 123 LayerBase::setName(name); 124 mSurfaceTexture->setName(name); 125} 126 127sp<ISurface> Layer::createSurface() 128{ 129 class BSurface : public BnSurface, public LayerCleaner { 130 wp<const Layer> mOwner; 131 virtual sp<ISurfaceTexture> getSurfaceTexture() const { 132 sp<ISurfaceTexture> res; 133 sp<const Layer> that( mOwner.promote() ); 134 if (that != NULL) { 135 res = that->mSurfaceTexture; 136 } 137 return res; 138 } 139 public: 140 BSurface(const sp<SurfaceFlinger>& flinger, 141 const sp<Layer>& layer) 142 : LayerCleaner(flinger, layer), mOwner(layer) { } 143 }; 144 sp<ISurface> sur(new BSurface(mFlinger, this)); 145 return sur; 146} 147 148wp<IBinder> Layer::getSurfaceTextureBinder() const 149{ 150 return mSurfaceTexture->asBinder(); 151} 152 153status_t Layer::setBuffers( uint32_t w, uint32_t h, 154 PixelFormat format, uint32_t flags) 155{ 156 // this surfaces pixel format 157 PixelFormatInfo info; 158 status_t err = getPixelFormatInfo(format, &info); 159 if (err) return err; 160 161 // the display's pixel format 162 const DisplayHardware& hw(graphicPlane(0).displayHardware()); 163 uint32_t const maxSurfaceDims = min( 164 hw.getMaxTextureSize(), hw.getMaxViewportDims()); 165 166 // never allow a surface larger than what our underlying GL implementation 167 // can handle. 168 if ((uint32_t(w)>maxSurfaceDims) || (uint32_t(h)>maxSurfaceDims)) { 169 return BAD_VALUE; 170 } 171 172 PixelFormatInfo displayInfo; 173 getPixelFormatInfo(hw.getFormat(), &displayInfo); 174 const uint32_t hwFlags = hw.getFlags(); 175 176 mFormat = format; 177 178 mSecure = (flags & ISurfaceComposer::eSecure) ? true : false; 179 mProtectedByApp = (flags & ISurfaceComposer::eProtectedByApp) ? true : false; 180 mOpaqueLayer = (flags & ISurfaceComposer::eOpaque); 181 mCurrentOpacity = getOpacityForFormat(format); 182 183 mSurfaceTexture->setDefaultBufferSize(w, h); 184 mSurfaceTexture->setDefaultBufferFormat(format); 185 186 // we use the red index 187 int displayRedSize = displayInfo.getSize(PixelFormatInfo::INDEX_RED); 188 int layerRedsize = info.getSize(PixelFormatInfo::INDEX_RED); 189 mNeedsDithering = layerRedsize > displayRedSize; 190 191 return NO_ERROR; 192} 193 194void Layer::setGeometry(hwc_layer_t* hwcl) 195{ 196 LayerBaseClient::setGeometry(hwcl); 197 198 hwcl->flags &= ~HWC_SKIP_LAYER; 199 200 // we can't do alpha-fade with the hwc HAL 201 const State& s(drawingState()); 202 if (s.alpha < 0xFF) { 203 hwcl->flags = HWC_SKIP_LAYER; 204 } 205 206 /* 207 * Transformations are applied in this order: 208 * 1) buffer orientation/flip/mirror 209 * 2) state transformation (window manager) 210 * 3) layer orientation (screen orientation) 211 * mTransform is already the composition of (2) and (3) 212 * (NOTE: the matrices are multiplied in reverse order) 213 */ 214 215 const Transform bufferOrientation(mCurrentTransform); 216 const Transform tr(mTransform * bufferOrientation); 217 218 // this gives us only the "orientation" component of the transform 219 const uint32_t finalTransform = tr.getOrientation(); 220 221 // we can only handle simple transformation 222 if (finalTransform & Transform::ROT_INVALID) { 223 hwcl->flags = HWC_SKIP_LAYER; 224 } else { 225 hwcl->transform = finalTransform; 226 } 227 228 if (isCropped()) { 229 hwcl->sourceCrop.left = mCurrentCrop.left; 230 hwcl->sourceCrop.top = mCurrentCrop.top; 231 hwcl->sourceCrop.right = mCurrentCrop.right; 232 hwcl->sourceCrop.bottom = mCurrentCrop.bottom; 233 } else { 234 const sp<GraphicBuffer>& buffer(mActiveBuffer); 235 hwcl->sourceCrop.left = 0; 236 hwcl->sourceCrop.top = 0; 237 if (buffer != NULL) { 238 hwcl->sourceCrop.right = buffer->width; 239 hwcl->sourceCrop.bottom = buffer->height; 240 } else { 241 hwcl->sourceCrop.right = mTransformedBounds.width(); 242 hwcl->sourceCrop.bottom = mTransformedBounds.height(); 243 } 244 } 245} 246 247void Layer::setPerFrameData(hwc_layer_t* hwcl) { 248 const sp<GraphicBuffer>& buffer(mActiveBuffer); 249 if (buffer == NULL) { 250 // this can happen if the client never drew into this layer yet, 251 // or if we ran out of memory. In that case, don't let 252 // HWC handle it. 253 hwcl->flags |= HWC_SKIP_LAYER; 254 hwcl->handle = NULL; 255 } else { 256 hwcl->handle = buffer->handle; 257 } 258} 259 260void Layer::onDraw(const Region& clip) const 261{ 262 if (CC_UNLIKELY(mActiveBuffer == 0)) { 263 // the texture has not been created yet, this Layer has 264 // in fact never been drawn into. This happens frequently with 265 // SurfaceView because the WindowManager can't know when the client 266 // has drawn the first time. 267 268 // If there is nothing under us, we paint the screen in black, otherwise 269 // we just skip this update. 270 271 // figure out if there is something below us 272 Region under; 273 const SurfaceFlinger::LayerVector& drawingLayers( 274 mFlinger->mDrawingState.layersSortedByZ); 275 const size_t count = drawingLayers.size(); 276 for (size_t i=0 ; i<count ; ++i) { 277 const sp<LayerBase>& layer(drawingLayers[i]); 278 if (layer.get() == static_cast<LayerBase const*>(this)) 279 break; 280 under.orSelf(layer->visibleRegionScreen); 281 } 282 // if not everything below us is covered, we plug the holes! 283 Region holes(clip.subtract(under)); 284 if (!holes.isEmpty()) { 285 clearWithOpenGL(holes, 0, 0, 0, 1); 286 } 287 return; 288 } 289 290 if (!isProtected()) { 291 glBindTexture(GL_TEXTURE_EXTERNAL_OES, mTextureName); 292 GLenum filter = GL_NEAREST; 293 if (getFiltering() || needsFiltering() || isFixedSize() || isCropped()) { 294 // TODO: we could be more subtle with isFixedSize() 295 filter = GL_LINEAR; 296 } 297 glTexParameterx(GL_TEXTURE_EXTERNAL_OES, GL_TEXTURE_MAG_FILTER, filter); 298 glTexParameterx(GL_TEXTURE_EXTERNAL_OES, GL_TEXTURE_MIN_FILTER, filter); 299 glMatrixMode(GL_TEXTURE); 300 glLoadMatrixf(mTextureMatrix); 301 glMatrixMode(GL_MODELVIEW); 302 glDisable(GL_TEXTURE_2D); 303 glEnable(GL_TEXTURE_EXTERNAL_OES); 304 } else { 305 glBindTexture(GL_TEXTURE_2D, mFlinger->getProtectedTexName()); 306 glMatrixMode(GL_TEXTURE); 307 glLoadIdentity(); 308 glMatrixMode(GL_MODELVIEW); 309 glDisable(GL_TEXTURE_EXTERNAL_OES); 310 glEnable(GL_TEXTURE_2D); 311 } 312 313 drawWithOpenGL(clip); 314 315 glDisable(GL_TEXTURE_EXTERNAL_OES); 316 glDisable(GL_TEXTURE_2D); 317} 318 319// As documented in libhardware header, formats in the range 320// 0x100 - 0x1FF are specific to the HAL implementation, and 321// are known to have no alpha channel 322// TODO: move definition for device-specific range into 323// hardware.h, instead of using hard-coded values here. 324#define HARDWARE_IS_DEVICE_FORMAT(f) ((f) >= 0x100 && (f) <= 0x1FF) 325 326bool Layer::getOpacityForFormat(uint32_t format) 327{ 328 if (HARDWARE_IS_DEVICE_FORMAT(format)) { 329 return true; 330 } 331 PixelFormatInfo info; 332 status_t err = getPixelFormatInfo(PixelFormat(format), &info); 333 // in case of error (unknown format), we assume no blending 334 return (err || info.h_alpha <= info.l_alpha); 335} 336 337 338bool Layer::isOpaque() const 339{ 340 // if we don't have a buffer yet, we're translucent regardless of the 341 // layer's opaque flag. 342 if (mActiveBuffer == 0) { 343 return false; 344 } 345 346 // if the layer has the opaque flag, then we're always opaque, 347 // otherwise we use the current buffer's format. 348 return mOpaqueLayer || mCurrentOpacity; 349} 350 351bool Layer::isProtected() const 352{ 353 const sp<GraphicBuffer>& activeBuffer(mActiveBuffer); 354 return (activeBuffer != 0) && 355 (activeBuffer->getUsage() & GRALLOC_USAGE_PROTECTED); 356} 357 358uint32_t Layer::doTransaction(uint32_t flags) 359{ 360 const Layer::State& front(drawingState()); 361 const Layer::State& temp(currentState()); 362 363 const bool sizeChanged = (front.requested_w != temp.requested_w) || 364 (front.requested_h != temp.requested_h); 365 366 if (sizeChanged) { 367 // the size changed, we need to ask our client to request a new buffer 368 ALOGD_IF(DEBUG_RESIZE, 369 "doTransaction: " 370 "resize (layer=%p), requested (%dx%d), drawing (%d,%d), " 371 "scalingMode=%d", 372 this, 373 int(temp.requested_w), int(temp.requested_h), 374 int(front.requested_w), int(front.requested_h), 375 mCurrentScalingMode); 376 377 if (!isFixedSize()) { 378 // this will make sure LayerBase::doTransaction doesn't update 379 // the drawing state's size 380 Layer::State& editDraw(mDrawingState); 381 editDraw.requested_w = temp.requested_w; 382 editDraw.requested_h = temp.requested_h; 383 } 384 385 // record the new size, form this point on, when the client request 386 // a buffer, it'll get the new size. 387 mSurfaceTexture->setDefaultBufferSize(temp.requested_w, 388 temp.requested_h); 389 } 390 391 return LayerBase::doTransaction(flags); 392} 393 394bool Layer::isFixedSize() const { 395 return mCurrentScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE; 396} 397 398bool Layer::isCropped() const { 399 return !mCurrentCrop.isEmpty(); 400} 401 402// ---------------------------------------------------------------------------- 403// pageflip handling... 404// ---------------------------------------------------------------------------- 405 406bool Layer::onPreComposition() 407{ 408 // if there was more than one pending update, request a refresh 409 if (mRefreshPending >= 2) { 410 mRefreshPending = 0; 411 return true; 412 } 413 mRefreshPending = 0; 414 return false; 415} 416 417void Layer::lockPageFlip(bool& recomputeVisibleRegions) 418{ 419 if (mQueuedFrames > 0) { 420 421 // if we've already called updateTexImage() without going through 422 // a composition step, we have to skip this layer at this point 423 // because we cannot call updateTeximage() without a corresponding 424 // compositionComplete() call. 425 // we'll trigger an update in onPreComposition(). 426 if (mRefreshPending++) { 427 return; 428 } 429 430 // Capture the old state of the layer for comparisons later 431 const bool oldOpacity = isOpaque(); 432 sp<GraphicBuffer> oldActiveBuffer = mActiveBuffer; 433 434 // signal another event if we have more frames pending 435 if (android_atomic_dec(&mQueuedFrames) > 1) { 436 mFlinger->signalLayerUpdate(); 437 } 438 439 if (mSurfaceTexture->updateTexImage() < NO_ERROR) { 440 // something happened! 441 recomputeVisibleRegions = true; 442 return; 443 } 444 445 // update the active buffer 446 mActiveBuffer = mSurfaceTexture->getCurrentBuffer(); 447 mFrameLatencyNeeded = true; 448 449 const Rect crop(mSurfaceTexture->getCurrentCrop()); 450 const uint32_t transform(mSurfaceTexture->getCurrentTransform()); 451 const uint32_t scalingMode(mSurfaceTexture->getCurrentScalingMode()); 452 if ((crop != mCurrentCrop) || 453 (transform != mCurrentTransform) || 454 (scalingMode != mCurrentScalingMode)) 455 { 456 mCurrentCrop = crop; 457 mCurrentTransform = transform; 458 mCurrentScalingMode = scalingMode; 459 mFlinger->invalidateHwcGeometry(); 460 } 461 462 GLfloat textureMatrix[16]; 463 mSurfaceTexture->getTransformMatrix(textureMatrix); 464 if (memcmp(textureMatrix, mTextureMatrix, sizeof(textureMatrix))) { 465 memcpy(mTextureMatrix, textureMatrix, sizeof(textureMatrix)); 466 mFlinger->invalidateHwcGeometry(); 467 } 468 469 uint32_t bufWidth = mActiveBuffer->getWidth(); 470 uint32_t bufHeight = mActiveBuffer->getHeight(); 471 if (oldActiveBuffer != NULL) { 472 if (bufWidth != uint32_t(oldActiveBuffer->width) || 473 bufHeight != uint32_t(oldActiveBuffer->height)) { 474 mFlinger->invalidateHwcGeometry(); 475 } 476 } 477 478 mCurrentOpacity = getOpacityForFormat(mActiveBuffer->format); 479 if (oldOpacity != isOpaque()) { 480 recomputeVisibleRegions = true; 481 } 482 483 glTexParameterx(GL_TEXTURE_EXTERNAL_OES, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 484 glTexParameterx(GL_TEXTURE_EXTERNAL_OES, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 485 486 // update the layer size if needed 487 const Layer::State& front(drawingState()); 488 489 // FIXME: mPostedDirtyRegion = dirty & bounds 490 mPostedDirtyRegion.set(front.w, front.h); 491 492 if ((front.w != front.requested_w) || 493 (front.h != front.requested_h)) 494 { 495 // check that we received a buffer of the right size 496 // (Take the buffer's orientation into account) 497 if (mCurrentTransform & Transform::ROT_90) { 498 swap(bufWidth, bufHeight); 499 } 500 501 if (isFixedSize() || 502 (bufWidth == front.requested_w && 503 bufHeight == front.requested_h)) 504 { 505 // Here we pretend the transaction happened by updating the 506 // current and drawing states. Drawing state is only accessed 507 // in this thread, no need to have it locked 508 Layer::State& editDraw(mDrawingState); 509 editDraw.w = editDraw.requested_w; 510 editDraw.h = editDraw.requested_h; 511 512 // We also need to update the current state so that we don't 513 // end-up doing too much work during the next transaction. 514 // NOTE: We actually don't need hold the transaction lock here 515 // because State::w and State::h are only accessed from 516 // this thread 517 Layer::State& editTemp(currentState()); 518 editTemp.w = editDraw.w; 519 editTemp.h = editDraw.h; 520 521 // recompute visible region 522 recomputeVisibleRegions = true; 523 } 524 525 ALOGD_IF(DEBUG_RESIZE, 526 "lockPageFlip : " 527 " (layer=%p), buffer (%ux%u, tr=%02x), " 528 "requested (%dx%d)", 529 this, 530 bufWidth, bufHeight, mCurrentTransform, 531 front.requested_w, front.requested_h); 532 } 533 } 534} 535 536void Layer::unlockPageFlip( 537 const Transform& planeTransform, Region& outDirtyRegion) 538{ 539 if (mRefreshPending >= 2) { 540 return; 541 } 542 543 Region dirtyRegion(mPostedDirtyRegion); 544 if (!dirtyRegion.isEmpty()) { 545 mPostedDirtyRegion.clear(); 546 // The dirty region is given in the layer's coordinate space 547 // transform the dirty region by the surface's transformation 548 // and the global transformation. 549 const Layer::State& s(drawingState()); 550 const Transform tr(planeTransform * s.transform); 551 dirtyRegion = tr.transform(dirtyRegion); 552 553 // At this point, the dirty region is in screen space. 554 // Make sure it's constrained by the visible region (which 555 // is in screen space as well). 556 dirtyRegion.andSelf(visibleRegionScreen); 557 outDirtyRegion.orSelf(dirtyRegion); 558 } 559} 560 561void Layer::dump(String8& result, char* buffer, size_t SIZE) const 562{ 563 LayerBaseClient::dump(result, buffer, SIZE); 564 565 sp<const GraphicBuffer> buf0(mActiveBuffer); 566 uint32_t w0=0, h0=0, s0=0, f0=0; 567 if (buf0 != 0) { 568 w0 = buf0->getWidth(); 569 h0 = buf0->getHeight(); 570 s0 = buf0->getStride(); 571 f0 = buf0->format; 572 } 573 snprintf(buffer, SIZE, 574 " " 575 "format=%2d, activeBuffer=[%4ux%4u:%4u,%3X]," 576 " transform-hint=0x%02x, queued-frames=%d, mRefreshPending=%d\n", 577 mFormat, w0, h0, s0,f0, 578 getTransformHint(), mQueuedFrames, mRefreshPending); 579 580 result.append(buffer); 581 582 if (mSurfaceTexture != 0) { 583 mSurfaceTexture->dump(result, " ", buffer, SIZE); 584 } 585} 586 587void Layer::dumpStats(String8& result, char* buffer, size_t SIZE) const 588{ 589 LayerBaseClient::dumpStats(result, buffer, SIZE); 590 const size_t o = mFrameLatencyOffset; 591 const DisplayHardware& hw(graphicPlane(0).displayHardware()); 592 const nsecs_t period = hw.getRefreshPeriod(); 593 result.appendFormat("%lld\n", period); 594 for (size_t i=0 ; i<128 ; i++) { 595 const size_t index = (o+i) % 128; 596 const nsecs_t time_app = mFrameStats[index].timestamp; 597 const nsecs_t time_set = mFrameStats[index].set; 598 const nsecs_t time_vsync = mFrameStats[index].vsync; 599 result.appendFormat("%lld\t%lld\t%lld\n", 600 time_app, 601 time_vsync, 602 time_set); 603 } 604 result.append("\n"); 605} 606 607void Layer::clearStats() 608{ 609 LayerBaseClient::clearStats(); 610 memset(mFrameStats, 0, sizeof(mFrameStats)); 611} 612 613uint32_t Layer::getEffectiveUsage(uint32_t usage) const 614{ 615 // TODO: should we do something special if mSecure is set? 616 if (mProtectedByApp) { 617 // need a hardware-protected path to external video sink 618 usage |= GraphicBuffer::USAGE_PROTECTED; 619 } 620 usage |= GraphicBuffer::USAGE_HW_COMPOSER; 621 return usage; 622} 623 624uint32_t Layer::getTransformHint() const { 625 uint32_t orientation = 0; 626 if (!mFlinger->mDebugDisableTransformHint) { 627 orientation = getPlaneOrientation(); 628 if (orientation & Transform::ROT_INVALID) { 629 orientation = 0; 630 } 631 } 632 return orientation; 633} 634 635// --------------------------------------------------------------------------- 636 637 638}; // namespace android 639