2 * Copyright (C) 2007 The Android Open Source Project
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
17 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
21 #include <sys/types.h>
24 #include <cutils/compiler.h>
25 #include <cutils/native_handle.h>
26 #include <cutils/properties.h>
28 #include <utils/Errors.h>
29 #include <utils/Log.h>
30 #include <utils/StopWatch.h>
31 #include <utils/Trace.h>
33 #include <ui/GraphicBuffer.h>
34 #include <ui/PixelFormat.h>
36 #include <gui/Surface.h>
39 #include "Colorizer.h"
40 #include "DisplayDevice.h"
42 #include "SurfaceFlinger.h"
43 #include "SurfaceTextureLayer.h"
45 #include "DisplayHardware/HWComposer.h"
47 #include "RenderEngine/RenderEngine.h"
49 #define DEBUG_RESIZE 0
53 // ---------------------------------------------------------------------------
55 int32_t Layer::sSequence = 1;
57 Layer::Layer(SurfaceFlinger* flinger, const sp<Client>& client,
58 const String8& name, uint32_t w, uint32_t h, uint32_t flags)
59 : contentDirty(false),
60 sequence(uint32_t(android_atomic_inc(&sSequence))),
63 mPremultipliedAlpha(true),
66 mFormat(PIXEL_FORMAT_NONE),
71 mCurrentScalingMode(NATIVE_WINDOW_SCALING_MODE_FREEZE),
72 mCurrentOpacity(true),
73 mRefreshPending(false),
74 mFrameLatencyNeeded(false),
76 mNeedsFiltering(false),
77 mMesh(Mesh::TRIANGLE_FAN, 4, 2, 2),
79 mProtectedByApp(false),
83 mCurrentCrop.makeInvalid();
84 mFlinger->getRenderEngine().genTextures(1, &mTextureName);
85 mTexture.init(Texture::TEXTURE_EXTERNAL, mTextureName);
87 uint32_t layerFlags = 0;
88 if (flags & ISurfaceComposerClient::eHidden)
89 layerFlags = layer_state_t::eLayerHidden;
91 if (flags & ISurfaceComposerClient::eNonPremultiplied)
92 mPremultipliedAlpha = false;
96 mCurrentState.active.w = w;
97 mCurrentState.active.h = h;
98 mCurrentState.active.crop.makeInvalid();
100 mCurrentState.alpha = 0xFF;
101 mCurrentState.layerStack = 0;
102 mCurrentState.flags = layerFlags;
103 mCurrentState.sequence = 0;
104 mCurrentState.transform.set(0, 0);
105 mCurrentState.requested = mCurrentState.active;
107 // drawing state & current state are identical
108 mDrawingState = mCurrentState;
110 nsecs_t displayPeriod =
111 flinger->getHwComposer().getRefreshPeriod(HWC_DISPLAY_PRIMARY);
112 mFrameTracker.setDisplayRefreshPeriod(displayPeriod);
115 void Layer::onFirstRef() {
116 // Creates a custom BufferQueue for SurfaceFlingerConsumer to use
117 mBufferQueue = new SurfaceTextureLayer(mFlinger);
118 mSurfaceFlingerConsumer = new SurfaceFlingerConsumer(mBufferQueue, mTextureName);
119 mSurfaceFlingerConsumer->setConsumerUsageBits(getEffectiveUsage(0));
120 mSurfaceFlingerConsumer->setFrameAvailableListener(this);
121 mSurfaceFlingerConsumer->setName(mName);
123 #ifdef TARGET_DISABLE_TRIPLE_BUFFERING
124 #warning "disabling triple buffering"
125 mSurfaceFlingerConsumer->setDefaultMaxBufferCount(2);
127 mSurfaceFlingerConsumer->setDefaultMaxBufferCount(3);
130 const sp<const DisplayDevice> hw(mFlinger->getDefaultDisplayDevice());
131 updateTransformHint(hw);
135 sp<Client> c(mClientRef.promote());
137 c->detachLayer(this);
139 mFlinger->deleteTextureAsync(mTextureName);
140 mFrameTracker.logAndResetStats(mName);
143 // ---------------------------------------------------------------------------
145 // ---------------------------------------------------------------------------
147 void Layer::onLayerDisplayed(const sp<const DisplayDevice>& hw,
148 HWComposer::HWCLayerInterface* layer) {
150 layer->onDisplayed();
151 mSurfaceFlingerConsumer->setReleaseFence(layer->getAndResetReleaseFence());
155 void Layer::onFrameAvailable() {
156 android_atomic_inc(&mQueuedFrames);
157 mFlinger->signalLayerUpdate();
160 // called with SurfaceFlinger::mStateLock from the drawing thread after
161 // the layer has been remove from the current state list (and just before
162 // it's removed from the drawing state list)
163 void Layer::onRemoved() {
164 mSurfaceFlingerConsumer->abandon();
167 // ---------------------------------------------------------------------------
169 // ---------------------------------------------------------------------------
171 const String8& Layer::getName() const {
175 status_t Layer::setBuffers( uint32_t w, uint32_t h,
176 PixelFormat format, uint32_t flags)
178 uint32_t const maxSurfaceDims = min(
179 mFlinger->getMaxTextureSize(), mFlinger->getMaxViewportDims());
181 // never allow a surface larger than what our underlying GL implementation
183 if ((uint32_t(w)>maxSurfaceDims) || (uint32_t(h)>maxSurfaceDims)) {
184 ALOGE("dimensions too large %u x %u", uint32_t(w), uint32_t(h));
190 mSecure = (flags & ISurfaceComposerClient::eSecure) ? true : false;
191 mProtectedByApp = (flags & ISurfaceComposerClient::eProtectedByApp) ? true : false;
192 mOpaqueLayer = (flags & ISurfaceComposerClient::eOpaque);
193 mCurrentOpacity = getOpacityForFormat(format);
195 mSurfaceFlingerConsumer->setDefaultBufferSize(w, h);
196 mSurfaceFlingerConsumer->setDefaultBufferFormat(format);
197 mSurfaceFlingerConsumer->setConsumerUsageBits(getEffectiveUsage(0));
202 sp<IBinder> Layer::getHandle() {
203 Mutex::Autolock _l(mLock);
205 LOG_ALWAYS_FATAL_IF(mHasSurface,
206 "Layer::getHandle() has already been called");
211 * The layer handle is just a BBinder object passed to the client
212 * (remote process) -- we don't keep any reference on our side such that
213 * the dtor is called when the remote side let go of its reference.
215 * LayerCleaner ensures that mFlinger->onLayerDestroyed() is called for
216 * this layer when the handle is destroyed.
219 class Handle : public BBinder, public LayerCleaner {
220 wp<const Layer> mOwner;
222 Handle(const sp<SurfaceFlinger>& flinger, const sp<Layer>& layer)
223 : LayerCleaner(flinger, layer), mOwner(layer) {
227 return new Handle(mFlinger, this);
230 sp<IGraphicBufferProducer> Layer::getBufferQueue() const {
234 // ---------------------------------------------------------------------------
235 // h/w composer set-up
236 // ---------------------------------------------------------------------------
238 Rect Layer::getContentCrop() const {
239 // this is the crop rectangle that applies to the buffer
240 // itself (as opposed to the window)
242 if (!mCurrentCrop.isEmpty()) {
243 // if the buffer crop is defined, we use that
245 } else if (mActiveBuffer != NULL) {
246 // otherwise we use the whole buffer
247 crop = mActiveBuffer->getBounds();
249 // if we don't have a buffer yet, we use an empty/invalid crop
255 static Rect reduce(const Rect& win, const Region& exclude) {
256 if (CC_LIKELY(exclude.isEmpty())) {
259 if (exclude.isRect()) {
260 return win.reduce(exclude.getBounds());
262 return Region(win).subtract(exclude).getBounds();
265 Rect Layer::computeBounds() const {
266 const Layer::State& s(getDrawingState());
267 Rect win(s.active.w, s.active.h);
268 if (!s.active.crop.isEmpty()) {
269 win.intersect(s.active.crop, &win);
271 // subtract the transparent region and snap to the bounds
272 return reduce(win, s.activeTransparentRegion);
275 FloatRect Layer::computeCrop(const sp<const DisplayDevice>& hw) const {
276 // the content crop is the area of the content that gets scaled to the
278 FloatRect crop(getContentCrop());
280 // the active.crop is the area of the window that gets cropped, but not
281 // scaled in any ways.
282 const State& s(getDrawingState());
284 // apply the projection's clipping to the window crop in
285 // layerstack space, and convert-back to layer space.
286 // if there are no window scaling involved, this operation will map to full
287 // pixels in the buffer.
288 // FIXME: the 3 lines below can produce slightly incorrect clipping when we have
289 // a viewport clipping and a window transform. we should use floating point to fix this.
291 Rect activeCrop(s.active.w, s.active.h);
292 if (!s.active.crop.isEmpty()) {
293 activeCrop = s.active.crop;
296 activeCrop = s.transform.transform(activeCrop);
297 activeCrop.intersect(hw->getViewport(), &activeCrop);
298 activeCrop = s.transform.inverse().transform(activeCrop);
300 // paranoia: make sure the window-crop is constrained in the
302 activeCrop.intersect(Rect(s.active.w, s.active.h), &activeCrop);
304 // subtract the transparent region and snap to the bounds
305 activeCrop = reduce(activeCrop, s.activeTransparentRegion);
307 if (!activeCrop.isEmpty()) {
308 // Transform the window crop to match the buffer coordinate system,
309 // which means using the inverse of the current transform set on the
310 // SurfaceFlingerConsumer.
311 uint32_t invTransform = mCurrentTransform;
312 int winWidth = s.active.w;
313 int winHeight = s.active.h;
314 if (invTransform & NATIVE_WINDOW_TRANSFORM_ROT_90) {
315 invTransform ^= NATIVE_WINDOW_TRANSFORM_FLIP_V |
316 NATIVE_WINDOW_TRANSFORM_FLIP_H;
317 winWidth = s.active.h;
318 winHeight = s.active.w;
320 const Rect winCrop = activeCrop.transform(
321 invTransform, s.active.w, s.active.h);
323 // below, crop is intersected with winCrop expressed in crop's coordinate space
324 float xScale = crop.getWidth() / float(winWidth);
325 float yScale = crop.getHeight() / float(winHeight);
327 float insetL = winCrop.left * xScale;
328 float insetT = winCrop.top * yScale;
329 float insetR = (winWidth - winCrop.right ) * xScale;
330 float insetB = (winHeight - winCrop.bottom) * yScale;
334 crop.right -= insetR;
335 crop.bottom -= insetB;
340 void Layer::setGeometry(
341 const sp<const DisplayDevice>& hw,
342 HWComposer::HWCLayerInterface& layer)
344 layer.setDefaultState();
347 layer.setSkip(false);
349 if (isSecure() && !hw->isSecure()) {
353 // this gives us only the "orientation" component of the transform
354 const State& s(getDrawingState());
355 if (!isOpaque() || s.alpha != 0xFF) {
356 layer.setBlending(mPremultipliedAlpha ?
357 HWC_BLENDING_PREMULT :
358 HWC_BLENDING_COVERAGE);
361 // apply the layer's transform, followed by the display's global transform
362 // here we're guaranteed that the layer's transform preserves rects
363 Rect frame(s.transform.transform(computeBounds()));
364 frame.intersect(hw->getViewport(), &frame);
365 const Transform& tr(hw->getTransform());
366 layer.setFrame(tr.transform(frame));
367 layer.setCrop(computeCrop(hw));
368 layer.setPlaneAlpha(s.alpha);
371 * Transformations are applied in this order:
372 * 1) buffer orientation/flip/mirror
373 * 2) state transformation (window manager)
374 * 3) layer orientation (screen orientation)
375 * (NOTE: the matrices are multiplied in reverse order)
378 const Transform bufferOrientation(mCurrentTransform);
379 const Transform transform(tr * s.transform * bufferOrientation);
381 // this gives us only the "orientation" component of the transform
382 const uint32_t orientation = transform.getOrientation();
383 if (orientation & Transform::ROT_INVALID) {
384 // we can only handle simple transformation
387 layer.setTransform(orientation);
391 void Layer::setPerFrameData(const sp<const DisplayDevice>& hw,
392 HWComposer::HWCLayerInterface& layer) {
393 // we have to set the visible region on every frame because
394 // we currently free it during onLayerDisplayed(), which is called
395 // after HWComposer::commit() -- every frame.
396 // Apply this display's projection's viewport to the visible region
397 // before giving it to the HWC HAL.
398 const Transform& tr = hw->getTransform();
399 Region visible = tr.transform(visibleRegion.intersect(hw->getViewport()));
400 layer.setVisibleRegionScreen(visible);
402 // NOTE: buffer can be NULL if the client never drew into this
403 // layer yet, or if we ran out of memory
404 layer.setBuffer(mActiveBuffer);
407 void Layer::setAcquireFence(const sp<const DisplayDevice>& hw,
408 HWComposer::HWCLayerInterface& layer) {
411 // TODO: there is a possible optimization here: we only need to set the
412 // acquire fence the first time a new buffer is acquired on EACH display.
414 if (layer.getCompositionType() == HWC_OVERLAY) {
415 sp<Fence> fence = mSurfaceFlingerConsumer->getCurrentFence();
416 if (fence->isValid()) {
417 fenceFd = fence->dup();
419 ALOGW("failed to dup layer fence, skipping sync: %d", errno);
423 layer.setAcquireFenceFd(fenceFd);
426 // ---------------------------------------------------------------------------
428 // ---------------------------------------------------------------------------
430 void Layer::draw(const sp<const DisplayDevice>& hw, const Region& clip) const {
434 void Layer::draw(const sp<const DisplayDevice>& hw) {
435 onDraw( hw, Region(hw->bounds()) );
438 void Layer::onDraw(const sp<const DisplayDevice>& hw, const Region& clip) const
442 if (CC_UNLIKELY(mActiveBuffer == 0)) {
443 // the texture has not been created yet, this Layer has
444 // in fact never been drawn into. This happens frequently with
445 // SurfaceView because the WindowManager can't know when the client
446 // has drawn the first time.
448 // If there is nothing under us, we paint the screen in black, otherwise
449 // we just skip this update.
451 // figure out if there is something below us
453 const SurfaceFlinger::LayerVector& drawingLayers(
454 mFlinger->mDrawingState.layersSortedByZ);
455 const size_t count = drawingLayers.size();
456 for (size_t i=0 ; i<count ; ++i) {
457 const sp<Layer>& layer(drawingLayers[i]);
458 if (layer.get() == static_cast<Layer const*>(this))
460 under.orSelf( hw->getTransform().transform(layer->visibleRegion) );
462 // if not everything below us is covered, we plug the holes!
463 Region holes(clip.subtract(under));
464 if (!holes.isEmpty()) {
465 clearWithOpenGL(hw, holes, 0, 0, 0, 1);
470 // Bind the current buffer to the GL texture, and wait for it to be
471 // ready for us to draw into.
472 status_t err = mSurfaceFlingerConsumer->bindTextureImage();
473 if (err != NO_ERROR) {
474 ALOGW("onDraw: bindTextureImage failed (err=%d)", err);
475 // Go ahead and draw the buffer anyway; no matter what we do the screen
476 // is probably going to have something visibly wrong.
479 bool blackOutLayer = isProtected() || (isSecure() && !hw->isSecure());
481 RenderEngine& engine(mFlinger->getRenderEngine());
483 if (!blackOutLayer) {
484 // TODO: we could be more subtle with isFixedSize()
485 const bool useFiltering = getFiltering() || needsFiltering(hw) || isFixedSize();
487 // Query the texture matrix given our current filtering mode.
488 float textureMatrix[16];
489 mSurfaceFlingerConsumer->setFilteringEnabled(useFiltering);
490 mSurfaceFlingerConsumer->getTransformMatrix(textureMatrix);
492 // Set things up for texturing.
493 mTexture.setDimensions(mActiveBuffer->getWidth(), mActiveBuffer->getHeight());
494 mTexture.setFiltering(useFiltering);
495 mTexture.setMatrix(textureMatrix);
497 engine.setupLayerTexturing(mTexture);
499 engine.setupLayerBlackedOut();
501 drawWithOpenGL(hw, clip);
502 engine.disableTexturing();
506 void Layer::clearWithOpenGL(const sp<const DisplayDevice>& hw, const Region& clip,
507 float red, float green, float blue, float alpha) const
509 RenderEngine& engine(mFlinger->getRenderEngine());
510 computeGeometry(hw, mMesh);
511 engine.setupFillWithColor(red, green, blue, alpha);
512 engine.drawMesh(mMesh);
515 void Layer::clearWithOpenGL(
516 const sp<const DisplayDevice>& hw, const Region& clip) const {
517 clearWithOpenGL(hw, clip, 0,0,0,0);
520 void Layer::drawWithOpenGL(
521 const sp<const DisplayDevice>& hw, const Region& clip) const {
522 const uint32_t fbHeight = hw->getHeight();
523 const State& s(getDrawingState());
525 computeGeometry(hw, mMesh);
528 * NOTE: the way we compute the texture coordinates here produces
529 * different results than when we take the HWC path -- in the later case
530 * the "source crop" is rounded to texel boundaries.
531 * This can produce significantly different results when the texture
532 * is scaled by a large amount.
534 * The GL code below is more logical (imho), and the difference with
535 * HWC is due to a limitation of the HWC API to integers -- a question
536 * is suspend is wether we should ignore this problem or revert to
537 * GL composition when a buffer scaling is applied (maybe with some
538 * minimal value)? Or, we could make GL behave like HWC -- but this feel
539 * like more of a hack.
541 const Rect win(computeBounds());
543 float left = float(win.left) / float(s.active.w);
544 float top = float(win.top) / float(s.active.h);
545 float right = float(win.right) / float(s.active.w);
546 float bottom = float(win.bottom) / float(s.active.h);
548 // TODO: we probably want to generate the texture coords with the mesh
549 // here we assume that we only have 4 vertices
550 Mesh::VertexArray texCoords(mMesh.getTexCoordArray());
551 texCoords[0].s = left;
552 texCoords[0].t = 1.0f - top;
553 texCoords[1].s = left;
554 texCoords[1].t = 1.0f - bottom;
555 texCoords[2].s = right;
556 texCoords[2].t = 1.0f - bottom;
557 texCoords[3].s = right;
558 texCoords[3].t = 1.0f - top;
560 RenderEngine& engine(mFlinger->getRenderEngine());
561 engine.setupLayerBlending(mPremultipliedAlpha, isOpaque(), s.alpha);
562 engine.drawMesh(mMesh);
563 engine.disableBlending();
566 void Layer::setFiltering(bool filtering) {
567 mFiltering = filtering;
570 bool Layer::getFiltering() const {
574 // As documented in libhardware header, formats in the range
575 // 0x100 - 0x1FF are specific to the HAL implementation, and
576 // are known to have no alpha channel
577 // TODO: move definition for device-specific range into
578 // hardware.h, instead of using hard-coded values here.
579 #define HARDWARE_IS_DEVICE_FORMAT(f) ((f) >= 0x100 && (f) <= 0x1FF)
581 bool Layer::getOpacityForFormat(uint32_t format) {
582 if (HARDWARE_IS_DEVICE_FORMAT(format)) {
586 case HAL_PIXEL_FORMAT_RGBA_8888:
587 case HAL_PIXEL_FORMAT_BGRA_8888:
588 case HAL_PIXEL_FORMAT_sRGB_A_8888:
591 // in all other case, we have no blending (also for unknown formats)
595 // ----------------------------------------------------------------------------
597 // ----------------------------------------------------------------------------
599 void Layer::computeGeometry(const sp<const DisplayDevice>& hw, Mesh& mesh) const
601 const Layer::State& s(getDrawingState());
602 const Transform tr(hw->getTransform() * s.transform);
603 const uint32_t hw_h = hw->getHeight();
604 Rect win(s.active.w, s.active.h);
605 if (!s.active.crop.isEmpty()) {
606 win.intersect(s.active.crop, &win);
608 // subtract the transparent region and snap to the bounds
609 win = reduce(win, s.activeTransparentRegion);
611 Mesh::VertexArray position(mesh.getPositionArray());
612 tr.transform(position[0], win.left, win.top);
613 tr.transform(position[1], win.left, win.bottom);
614 tr.transform(position[2], win.right, win.bottom);
615 tr.transform(position[3], win.right, win.top);
616 for (size_t i=0 ; i<4 ; i++) {
617 position[i].y = hw_h - position[i].y;
621 bool Layer::isOpaque() const
623 // if we don't have a buffer yet, we're translucent regardless of the
624 // layer's opaque flag.
625 if (mActiveBuffer == 0) {
629 // if the layer has the opaque flag, then we're always opaque,
630 // otherwise we use the current buffer's format.
631 return mOpaqueLayer || mCurrentOpacity;
634 bool Layer::isProtected() const
636 const sp<GraphicBuffer>& activeBuffer(mActiveBuffer);
637 return (activeBuffer != 0) &&
638 (activeBuffer->getUsage() & GRALLOC_USAGE_PROTECTED);
641 bool Layer::isFixedSize() const {
642 return mCurrentScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE;
645 bool Layer::isCropped() const {
646 return !mCurrentCrop.isEmpty();
649 bool Layer::needsFiltering(const sp<const DisplayDevice>& hw) const {
650 return mNeedsFiltering || hw->needsFiltering();
653 void Layer::setVisibleRegion(const Region& visibleRegion) {
654 // always called from main thread
655 this->visibleRegion = visibleRegion;
658 void Layer::setCoveredRegion(const Region& coveredRegion) {
659 // always called from main thread
660 this->coveredRegion = coveredRegion;
663 void Layer::setVisibleNonTransparentRegion(const Region&
664 setVisibleNonTransparentRegion) {
665 // always called from main thread
666 this->visibleNonTransparentRegion = setVisibleNonTransparentRegion;
669 // ----------------------------------------------------------------------------
671 // ----------------------------------------------------------------------------
673 uint32_t Layer::doTransaction(uint32_t flags) {
676 const Layer::State& s(getDrawingState());
677 const Layer::State& c(getCurrentState());
679 const bool sizeChanged = (c.requested.w != s.requested.w) ||
680 (c.requested.h != s.requested.h);
683 // the size changed, we need to ask our client to request a new buffer
684 ALOGD_IF(DEBUG_RESIZE,
685 "doTransaction: geometry (layer=%p '%s'), tr=%02x, scalingMode=%d\n"
686 " current={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n"
687 " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n"
688 " drawing={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n"
689 " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n",
690 this, getName().string(), mCurrentTransform, mCurrentScalingMode,
691 c.active.w, c.active.h,
695 c.active.crop.bottom,
696 c.active.crop.getWidth(),
697 c.active.crop.getHeight(),
698 c.requested.w, c.requested.h,
699 c.requested.crop.left,
700 c.requested.crop.top,
701 c.requested.crop.right,
702 c.requested.crop.bottom,
703 c.requested.crop.getWidth(),
704 c.requested.crop.getHeight(),
705 s.active.w, s.active.h,
709 s.active.crop.bottom,
710 s.active.crop.getWidth(),
711 s.active.crop.getHeight(),
712 s.requested.w, s.requested.h,
713 s.requested.crop.left,
714 s.requested.crop.top,
715 s.requested.crop.right,
716 s.requested.crop.bottom,
717 s.requested.crop.getWidth(),
718 s.requested.crop.getHeight());
720 // record the new size, form this point on, when the client request
721 // a buffer, it'll get the new size.
722 mSurfaceFlingerConsumer->setDefaultBufferSize(
723 c.requested.w, c.requested.h);
726 if (!isFixedSize()) {
728 const bool resizePending = (c.requested.w != c.active.w) ||
729 (c.requested.h != c.active.h);
732 // don't let Layer::doTransaction update the drawing state
733 // if we have a pending resize, unless we are in fixed-size mode.
734 // the drawing state will be updated only once we receive a buffer
735 // with the correct size.
737 // in particular, we want to make sure the clip (which is part
738 // of the geometry state) is latched together with the size but is
739 // latched immediately when no resizing is involved.
741 flags |= eDontUpdateGeometryState;
745 // always set active to requested, unless we're asked not to
746 // this is used by Layer, which special cases resizes.
747 if (flags & eDontUpdateGeometryState) {
749 Layer::State& editCurrentState(getCurrentState());
750 editCurrentState.active = c.requested;
753 if (s.active != c.active) {
754 // invalidate and recompute the visible regions if needed
755 flags |= Layer::eVisibleRegion;
758 if (c.sequence != s.sequence) {
759 // invalidate and recompute the visible regions if needed
760 flags |= eVisibleRegion;
761 this->contentDirty = true;
763 // we may use linear filtering, if the matrix scales us
764 const uint8_t type = c.transform.getType();
765 mNeedsFiltering = (!c.transform.preserveRects() ||
766 (type >= Transform::SCALE));
769 // Commit the transaction
774 void Layer::commitTransaction() {
775 mDrawingState = mCurrentState;
778 uint32_t Layer::getTransactionFlags(uint32_t flags) {
779 return android_atomic_and(~flags, &mTransactionFlags) & flags;
782 uint32_t Layer::setTransactionFlags(uint32_t flags) {
783 return android_atomic_or(flags, &mTransactionFlags);
786 bool Layer::setPosition(float x, float y) {
787 if (mCurrentState.transform.tx() == x && mCurrentState.transform.ty() == y)
789 mCurrentState.sequence++;
790 mCurrentState.transform.set(x, y);
791 setTransactionFlags(eTransactionNeeded);
794 bool Layer::setLayer(uint32_t z) {
795 if (mCurrentState.z == z)
797 mCurrentState.sequence++;
799 setTransactionFlags(eTransactionNeeded);
802 bool Layer::setSize(uint32_t w, uint32_t h) {
803 if (mCurrentState.requested.w == w && mCurrentState.requested.h == h)
805 mCurrentState.requested.w = w;
806 mCurrentState.requested.h = h;
807 setTransactionFlags(eTransactionNeeded);
810 bool Layer::setAlpha(uint8_t alpha) {
811 if (mCurrentState.alpha == alpha)
813 mCurrentState.sequence++;
814 mCurrentState.alpha = alpha;
815 setTransactionFlags(eTransactionNeeded);
818 bool Layer::setMatrix(const layer_state_t::matrix22_t& matrix) {
819 mCurrentState.sequence++;
820 mCurrentState.transform.set(
821 matrix.dsdx, matrix.dsdy, matrix.dtdx, matrix.dtdy);
822 setTransactionFlags(eTransactionNeeded);
825 bool Layer::setTransparentRegionHint(const Region& transparent) {
826 mCurrentState.requestedTransparentRegion = transparent;
827 setTransactionFlags(eTransactionNeeded);
830 bool Layer::setFlags(uint8_t flags, uint8_t mask) {
831 const uint32_t newFlags = (mCurrentState.flags & ~mask) | (flags & mask);
832 if (mCurrentState.flags == newFlags)
834 mCurrentState.sequence++;
835 mCurrentState.flags = newFlags;
836 setTransactionFlags(eTransactionNeeded);
839 bool Layer::setCrop(const Rect& crop) {
840 if (mCurrentState.requested.crop == crop)
842 mCurrentState.sequence++;
843 mCurrentState.requested.crop = crop;
844 setTransactionFlags(eTransactionNeeded);
848 bool Layer::setLayerStack(uint32_t layerStack) {
849 if (mCurrentState.layerStack == layerStack)
851 mCurrentState.sequence++;
852 mCurrentState.layerStack = layerStack;
853 setTransactionFlags(eTransactionNeeded);
857 // ----------------------------------------------------------------------------
858 // pageflip handling...
859 // ----------------------------------------------------------------------------
861 bool Layer::onPreComposition() {
862 mRefreshPending = false;
863 return mQueuedFrames > 0;
866 void Layer::onPostComposition() {
867 if (mFrameLatencyNeeded) {
868 nsecs_t desiredPresentTime = mSurfaceFlingerConsumer->getTimestamp();
869 mFrameTracker.setDesiredPresentTime(desiredPresentTime);
871 sp<Fence> frameReadyFence = mSurfaceFlingerConsumer->getCurrentFence();
872 if (frameReadyFence->isValid()) {
873 mFrameTracker.setFrameReadyFence(frameReadyFence);
875 // There was no fence for this frame, so assume that it was ready
876 // to be presented at the desired present time.
877 mFrameTracker.setFrameReadyTime(desiredPresentTime);
880 const HWComposer& hwc = mFlinger->getHwComposer();
881 sp<Fence> presentFence = hwc.getDisplayFence(HWC_DISPLAY_PRIMARY);
882 if (presentFence->isValid()) {
883 mFrameTracker.setActualPresentFence(presentFence);
885 // The HWC doesn't support present fences, so use the refresh
886 // timestamp instead.
887 nsecs_t presentTime = hwc.getRefreshTimestamp(HWC_DISPLAY_PRIMARY);
888 mFrameTracker.setActualPresentTime(presentTime);
891 mFrameTracker.advanceFrame();
892 mFrameLatencyNeeded = false;
896 bool Layer::isVisible() const {
897 const Layer::State& s(mDrawingState);
898 return !(s.flags & layer_state_t::eLayerHidden) && s.alpha
899 && (mActiveBuffer != NULL);
902 Region Layer::latchBuffer(bool& recomputeVisibleRegions)
906 Region outDirtyRegion;
907 if (mQueuedFrames > 0) {
909 // if we've already called updateTexImage() without going through
910 // a composition step, we have to skip this layer at this point
911 // because we cannot call updateTeximage() without a corresponding
912 // compositionComplete() call.
913 // we'll trigger an update in onPreComposition().
914 if (mRefreshPending) {
915 return outDirtyRegion;
918 // Capture the old state of the layer for comparisons later
919 const bool oldOpacity = isOpaque();
920 sp<GraphicBuffer> oldActiveBuffer = mActiveBuffer;
922 struct Reject : public SurfaceFlingerConsumer::BufferRejecter {
924 Layer::State& current;
925 bool& recomputeVisibleRegions;
926 Reject(Layer::State& front, Layer::State& current,
927 bool& recomputeVisibleRegions)
928 : front(front), current(current),
929 recomputeVisibleRegions(recomputeVisibleRegions) {
932 virtual bool reject(const sp<GraphicBuffer>& buf,
933 const IGraphicBufferConsumer::BufferItem& item) {
938 uint32_t bufWidth = buf->getWidth();
939 uint32_t bufHeight = buf->getHeight();
941 // check that we received a buffer of the right size
942 // (Take the buffer's orientation into account)
943 if (item.mTransform & Transform::ROT_90) {
944 swap(bufWidth, bufHeight);
947 bool isFixedSize = item.mScalingMode != NATIVE_WINDOW_SCALING_MODE_FREEZE;
948 if (front.active != front.requested) {
951 (bufWidth == front.requested.w &&
952 bufHeight == front.requested.h))
954 // Here we pretend the transaction happened by updating the
955 // current and drawing states. Drawing state is only accessed
956 // in this thread, no need to have it locked
957 front.active = front.requested;
959 // We also need to update the current state so that
960 // we don't end-up overwriting the drawing state with
961 // this stale current state during the next transaction
963 // NOTE: We don't need to hold the transaction lock here
964 // because State::active is only accessed from this thread.
965 current.active = front.active;
967 // recompute visible region
968 recomputeVisibleRegions = true;
971 ALOGD_IF(DEBUG_RESIZE,
972 "latchBuffer/reject: buffer (%ux%u, tr=%02x), scalingMode=%d\n"
973 " drawing={ active ={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }\n"
974 " requested={ wh={%4u,%4u} crop={%4d,%4d,%4d,%4d} (%4d,%4d) }}\n",
975 bufWidth, bufHeight, item.mTransform, item.mScalingMode,
976 front.active.w, front.active.h,
977 front.active.crop.left,
978 front.active.crop.top,
979 front.active.crop.right,
980 front.active.crop.bottom,
981 front.active.crop.getWidth(),
982 front.active.crop.getHeight(),
983 front.requested.w, front.requested.h,
984 front.requested.crop.left,
985 front.requested.crop.top,
986 front.requested.crop.right,
987 front.requested.crop.bottom,
988 front.requested.crop.getWidth(),
989 front.requested.crop.getHeight());
993 if (front.active.w != bufWidth ||
994 front.active.h != bufHeight) {
995 // reject this buffer
996 //ALOGD("rejecting buffer: bufWidth=%d, bufHeight=%d, front.active.{w=%d, h=%d}",
997 // bufWidth, bufHeight, front.active.w, front.active.h);
1002 // if the transparent region has changed (this test is
1003 // conservative, but that's fine, worst case we're doing
1004 // a bit of extra work), we latch the new one and we
1005 // trigger a visible-region recompute.
1006 if (!front.activeTransparentRegion.isTriviallyEqual(
1007 front.requestedTransparentRegion)) {
1008 front.activeTransparentRegion = front.requestedTransparentRegion;
1010 // We also need to update the current state so that
1011 // we don't end-up overwriting the drawing state with
1012 // this stale current state during the next transaction
1014 // NOTE: We don't need to hold the transaction lock here
1015 // because State::active is only accessed from this thread.
1016 current.activeTransparentRegion = front.activeTransparentRegion;
1018 // recompute visible region
1019 recomputeVisibleRegions = true;
1027 Reject r(mDrawingState, getCurrentState(), recomputeVisibleRegions);
1029 status_t updateResult = mSurfaceFlingerConsumer->updateTexImage(&r);
1030 if (updateResult == BufferQueue::PRESENT_LATER) {
1031 // Producer doesn't want buffer to be displayed yet. Signal a
1032 // layer update so we check again at the next opportunity.
1033 mFlinger->signalLayerUpdate();
1034 return outDirtyRegion;
1037 // Decrement the queued-frames count. Signal another event if we
1038 // have more frames pending.
1039 if (android_atomic_dec(&mQueuedFrames) > 1) {
1040 mFlinger->signalLayerUpdate();
1043 if (updateResult != NO_ERROR) {
1044 // something happened!
1045 recomputeVisibleRegions = true;
1046 return outDirtyRegion;
1049 // update the active buffer
1050 mActiveBuffer = mSurfaceFlingerConsumer->getCurrentBuffer();
1051 if (mActiveBuffer == NULL) {
1052 // this can only happen if the very first buffer was rejected.
1053 return outDirtyRegion;
1056 mRefreshPending = true;
1057 mFrameLatencyNeeded = true;
1058 if (oldActiveBuffer == NULL) {
1059 // the first time we receive a buffer, we need to trigger a
1060 // geometry invalidation.
1061 recomputeVisibleRegions = true;
1064 Rect crop(mSurfaceFlingerConsumer->getCurrentCrop());
1065 const uint32_t transform(mSurfaceFlingerConsumer->getCurrentTransform());
1066 const uint32_t scalingMode(mSurfaceFlingerConsumer->getCurrentScalingMode());
1067 if ((crop != mCurrentCrop) ||
1068 (transform != mCurrentTransform) ||
1069 (scalingMode != mCurrentScalingMode))
1071 mCurrentCrop = crop;
1072 mCurrentTransform = transform;
1073 mCurrentScalingMode = scalingMode;
1074 recomputeVisibleRegions = true;
1077 if (oldActiveBuffer != NULL) {
1078 uint32_t bufWidth = mActiveBuffer->getWidth();
1079 uint32_t bufHeight = mActiveBuffer->getHeight();
1080 if (bufWidth != uint32_t(oldActiveBuffer->width) ||
1081 bufHeight != uint32_t(oldActiveBuffer->height)) {
1082 recomputeVisibleRegions = true;
1086 mCurrentOpacity = getOpacityForFormat(mActiveBuffer->format);
1087 if (oldOpacity != isOpaque()) {
1088 recomputeVisibleRegions = true;
1091 // FIXME: postedRegion should be dirty & bounds
1092 const Layer::State& s(getDrawingState());
1093 Region dirtyRegion(Rect(s.active.w, s.active.h));
1095 // transform the dirty region to window-manager space
1096 outDirtyRegion = (s.transform.transform(dirtyRegion));
1098 return outDirtyRegion;
1101 uint32_t Layer::getEffectiveUsage(uint32_t usage) const
1103 // TODO: should we do something special if mSecure is set?
1104 if (mProtectedByApp) {
1105 // need a hardware-protected path to external video sink
1106 usage |= GraphicBuffer::USAGE_PROTECTED;
1108 usage |= GraphicBuffer::USAGE_HW_COMPOSER;
1112 void Layer::updateTransformHint(const sp<const DisplayDevice>& hw) const {
1113 uint32_t orientation = 0;
1114 if (!mFlinger->mDebugDisableTransformHint) {
1115 // The transform hint is used to improve performance, but we can
1116 // only have a single transform hint, it cannot
1117 // apply to all displays.
1118 const Transform& planeTransform(hw->getTransform());
1119 orientation = planeTransform.getOrientation();
1120 if (orientation & Transform::ROT_INVALID) {
1124 mSurfaceFlingerConsumer->setTransformHint(orientation);
1127 // ----------------------------------------------------------------------------
1129 // ----------------------------------------------------------------------------
1131 void Layer::dump(String8& result, Colorizer& colorizer) const
1133 const Layer::State& s(getDrawingState());
1135 colorizer.colorize(result, Colorizer::GREEN);
1136 result.appendFormat(
1138 getTypeId(), this, getName().string());
1139 colorizer.reset(result);
1141 s.activeTransparentRegion.dump(result, "transparentRegion");
1142 visibleRegion.dump(result, "visibleRegion");
1143 sp<Client> client(mClientRef.promote());
1145 result.appendFormat( " "
1146 "layerStack=%4d, z=%9d, pos=(%g,%g), size=(%4d,%4d), crop=(%4d,%4d,%4d,%4d), "
1147 "isOpaque=%1d, invalidate=%1d, "
1148 "alpha=0x%02x, flags=0x%08x, tr=[%.2f, %.2f][%.2f, %.2f]\n"
1150 s.layerStack, s.z, s.transform.tx(), s.transform.ty(), s.active.w, s.active.h,
1151 s.active.crop.left, s.active.crop.top,
1152 s.active.crop.right, s.active.crop.bottom,
1153 isOpaque(), contentDirty,
1155 s.transform[0][0], s.transform[0][1],
1156 s.transform[1][0], s.transform[1][1],
1159 sp<const GraphicBuffer> buf0(mActiveBuffer);
1160 uint32_t w0=0, h0=0, s0=0, f0=0;
1162 w0 = buf0->getWidth();
1163 h0 = buf0->getHeight();
1164 s0 = buf0->getStride();
1167 result.appendFormat(
1169 "format=%2d, activeBuffer=[%4ux%4u:%4u,%3X],"
1170 " queued-frames=%d, mRefreshPending=%d\n",
1171 mFormat, w0, h0, s0,f0,
1172 mQueuedFrames, mRefreshPending);
1174 if (mSurfaceFlingerConsumer != 0) {
1175 mSurfaceFlingerConsumer->dump(result, " ");
1179 void Layer::dumpStats(String8& result) const {
1180 mFrameTracker.dump(result);
1183 void Layer::clearStats() {
1184 mFrameTracker.clear();
1187 void Layer::logFrameStats() {
1188 mFrameTracker.logAndResetStats(mName);
1191 // ---------------------------------------------------------------------------
1193 Layer::LayerCleaner::LayerCleaner(const sp<SurfaceFlinger>& flinger,
1194 const sp<Layer>& layer)
1195 : mFlinger(flinger), mLayer(layer) {
1198 Layer::LayerCleaner::~LayerCleaner() {
1199 // destroy client resources
1200 mFlinger->onLayerDestroyed(mLayer);
1203 // ---------------------------------------------------------------------------
1204 }; // namespace android
1206 #if defined(__gl_h_)
1207 #error "don't include gl/gl.h in this file"
1210 #if defined(__gl2_h_)
1211 #error "don't include gl2/gl2.h in this file"