blob: ea685e7171c6d3a7d62e2515ab52b0d9e6475c8c [file] [log] [blame]
Dan Stoza9e56aa02015-11-02 13:00:03 -08001/*
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 <stdint.h>
20#include <sys/types.h>
21#include <errno.h>
22#include <math.h>
23#include <dlfcn.h>
24#include <inttypes.h>
25#include <stdatomic.h>
26
27#include <EGL/egl.h>
28
29#include <cutils/log.h>
30#include <cutils/properties.h>
31
32#include <binder/IPCThreadState.h>
33#include <binder/IServiceManager.h>
34#include <binder/MemoryHeapBase.h>
35#include <binder/PermissionCache.h>
36
37#include <ui/DisplayInfo.h>
38#include <ui/DisplayStatInfo.h>
39
40#include <gui/BitTube.h>
41#include <gui/BufferQueue.h>
42#include <gui/GuiConfig.h>
43#include <gui/IDisplayEventConnection.h>
44#include <gui/Surface.h>
45#include <gui/GraphicBufferAlloc.h>
46
47#include <ui/GraphicBufferAllocator.h>
Dan Stozac4f471e2016-03-24 09:31:08 -070048#include <ui/HdrCapabilities.h>
Dan Stoza9e56aa02015-11-02 13:00:03 -080049#include <ui/PixelFormat.h>
50#include <ui/UiConfig.h>
51
52#include <utils/misc.h>
53#include <utils/String8.h>
54#include <utils/String16.h>
55#include <utils/StopWatch.h>
56#include <utils/Timers.h>
57#include <utils/Trace.h>
58
59#include <private/android_filesystem_config.h>
60#include <private/gui/SyncFeatures.h>
61
62#include "Client.h"
63#include "clz.h"
64#include "Colorizer.h"
65#include "DdmConnection.h"
66#include "DisplayDevice.h"
67#include "DispSync.h"
68#include "EventControlThread.h"
69#include "EventThread.h"
70#include "Layer.h"
71#include "LayerDim.h"
72#include "SurfaceFlinger.h"
73
74#include "DisplayHardware/FramebufferSurface.h"
75#include "DisplayHardware/HWComposer.h"
76#include "DisplayHardware/VirtualDisplaySurface.h"
77
78#include "Effects/Daltonizer.h"
79
80#include "RenderEngine/RenderEngine.h"
81#include <cutils/compiler.h>
82
83#define DISPLAY_COUNT 1
84
85/*
86 * DEBUG_SCREENSHOTS: set to true to check that screenshots are not all
87 * black pixels.
88 */
89#define DEBUG_SCREENSHOTS false
90
91EGLAPI const char* eglQueryStringImplementationANDROID(EGLDisplay dpy, EGLint name);
92
93namespace android {
94
95// This is the phase offset in nanoseconds of the software vsync event
96// relative to the vsync event reported by HWComposer. The software vsync
97// event is when SurfaceFlinger and Choreographer-based applications run each
98// frame.
99//
100// This phase offset allows adjustment of the minimum latency from application
101// wake-up (by Choregographer) time to the time at which the resulting window
102// image is displayed. This value may be either positive (after the HW vsync)
103// or negative (before the HW vsync). Setting it to 0 will result in a
104// minimum latency of two vsync periods because the app and SurfaceFlinger
105// will run just after the HW vsync. Setting it to a positive number will
106// result in the minimum latency being:
107//
108// (2 * VSYNC_PERIOD - (vsyncPhaseOffsetNs % VSYNC_PERIOD))
109//
110// Note that reducing this latency makes it more likely for the applications
111// to not have their window content image ready in time. When this happens
112// the latency will end up being an additional vsync period, and animations
113// will hiccup. Therefore, this latency should be tuned somewhat
114// conservatively (or at least with awareness of the trade-off being made).
115static const int64_t vsyncPhaseOffsetNs = VSYNC_EVENT_PHASE_OFFSET_NS;
116
117// This is the phase offset at which SurfaceFlinger's composition runs.
118static const int64_t sfVsyncPhaseOffsetNs = SF_VSYNC_EVENT_PHASE_OFFSET_NS;
119
120// ---------------------------------------------------------------------------
121
122const String16 sHardwareTest("android.permission.HARDWARE_TEST");
123const String16 sAccessSurfaceFlinger("android.permission.ACCESS_SURFACE_FLINGER");
124const String16 sReadFramebuffer("android.permission.READ_FRAME_BUFFER");
125const String16 sDump("android.permission.DUMP");
126
127// ---------------------------------------------------------------------------
128
129SurfaceFlinger::SurfaceFlinger()
130 : BnSurfaceComposer(),
131 mTransactionFlags(0),
132 mTransactionPending(false),
133 mAnimTransactionPending(false),
134 mLayersRemoved(false),
135 mRepaintEverything(0),
136 mRenderEngine(NULL),
137 mBootTime(systemTime()),
138 mVisibleRegionsDirty(false),
139 mHwWorkListDirty(false),
140 mAnimCompositionPending(false),
141 mDebugRegion(0),
142 mDebugDDMS(0),
143 mDebugDisableHWC(0),
144 mDebugDisableTransformHint(0),
145 mDebugInSwapBuffers(0),
146 mLastSwapBufferTime(0),
147 mDebugInTransaction(0),
148 mLastTransactionTime(0),
149 mBootFinished(false),
150 mForceFullDamage(false),
Dan Stozaf34b9be2016-04-05 16:45:26 -0700151 mPrimaryDispSync("PrimaryDispSync"),
Dan Stoza9e56aa02015-11-02 13:00:03 -0800152 mPrimaryHWVsyncEnabled(false),
153 mHWVsyncAvailable(false),
154 mDaltonize(false),
155 mHasColorMatrix(false),
156 mHasPoweredOff(false),
157 mFrameBuckets(),
158 mTotalTime(0),
159 mLastSwapTime(0)
160{
161 ALOGI("SurfaceFlinger is starting");
162
163 // debugging stuff...
164 char value[PROPERTY_VALUE_MAX];
165
166 property_get("ro.bq.gpu_to_cpu_unsupported", value, "0");
167 mGpuToCpuSupported = !atoi(value);
168
169 property_get("debug.sf.drop_missed_frames", value, "0");
170 mDropMissedFrames = atoi(value);
171
172 property_get("debug.sf.showupdates", value, "0");
173 mDebugRegion = atoi(value);
174
175 property_get("debug.sf.ddms", value, "0");
176 mDebugDDMS = atoi(value);
177 if (mDebugDDMS) {
178 if (!startDdmConnection()) {
179 // start failed, and DDMS debugging not enabled
180 mDebugDDMS = 0;
181 }
182 }
183 ALOGI_IF(mDebugRegion, "showupdates enabled");
184 ALOGI_IF(mDebugDDMS, "DDMS debugging enabled");
185}
186
187void SurfaceFlinger::onFirstRef()
188{
189 mEventQueue.init(this);
190}
191
192SurfaceFlinger::~SurfaceFlinger()
193{
194 EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
195 eglMakeCurrent(display, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
196 eglTerminate(display);
197}
198
199void SurfaceFlinger::binderDied(const wp<IBinder>& /* who */)
200{
201 // the window manager died on us. prepare its eulogy.
202
203 // restore initial conditions (default device unblank, etc)
204 initializeDisplays();
205
206 // restart the boot-animation
207 startBootAnim();
208}
209
210sp<ISurfaceComposerClient> SurfaceFlinger::createConnection()
211{
212 sp<ISurfaceComposerClient> bclient;
213 sp<Client> client(new Client(this));
214 status_t err = client->initCheck();
215 if (err == NO_ERROR) {
216 bclient = client;
217 }
218 return bclient;
219}
220
221sp<IBinder> SurfaceFlinger::createDisplay(const String8& displayName,
222 bool secure)
223{
224 class DisplayToken : public BBinder {
225 sp<SurfaceFlinger> flinger;
226 virtual ~DisplayToken() {
227 // no more references, this display must be terminated
228 Mutex::Autolock _l(flinger->mStateLock);
229 flinger->mCurrentState.displays.removeItem(this);
230 flinger->setTransactionFlags(eDisplayTransactionNeeded);
231 }
232 public:
233 DisplayToken(const sp<SurfaceFlinger>& flinger)
234 : flinger(flinger) {
235 }
236 };
237
238 sp<BBinder> token = new DisplayToken(this);
239
240 Mutex::Autolock _l(mStateLock);
241 DisplayDeviceState info(DisplayDevice::DISPLAY_VIRTUAL, secure);
242 info.displayName = displayName;
243 mCurrentState.displays.add(token, info);
244
245 return token;
246}
247
248void SurfaceFlinger::destroyDisplay(const sp<IBinder>& display) {
249 Mutex::Autolock _l(mStateLock);
250
251 ssize_t idx = mCurrentState.displays.indexOfKey(display);
252 if (idx < 0) {
253 ALOGW("destroyDisplay: invalid display token");
254 return;
255 }
256
257 const DisplayDeviceState& info(mCurrentState.displays.valueAt(idx));
258 if (!info.isVirtualDisplay()) {
259 ALOGE("destroyDisplay called for non-virtual display");
260 return;
261 }
262
263 mCurrentState.displays.removeItemsAt(idx);
264 setTransactionFlags(eDisplayTransactionNeeded);
265}
266
267void SurfaceFlinger::createBuiltinDisplayLocked(DisplayDevice::DisplayType type) {
268 ALOGW_IF(mBuiltinDisplays[type],
269 "Overwriting display token for display type %d", type);
270 mBuiltinDisplays[type] = new BBinder();
271 // All non-virtual displays are currently considered secure.
272 DisplayDeviceState info(type, true);
273 mCurrentState.displays.add(mBuiltinDisplays[type], info);
274}
275
276sp<IBinder> SurfaceFlinger::getBuiltInDisplay(int32_t id) {
277 if (uint32_t(id) >= DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES) {
278 ALOGE("getDefaultDisplay: id=%d is not a valid default display id", id);
279 return NULL;
280 }
281 return mBuiltinDisplays[id];
282}
283
284sp<IGraphicBufferAlloc> SurfaceFlinger::createGraphicBufferAlloc()
285{
286 sp<GraphicBufferAlloc> gba(new GraphicBufferAlloc());
287 return gba;
288}
289
290void SurfaceFlinger::bootFinished()
291{
292 const nsecs_t now = systemTime();
293 const nsecs_t duration = now - mBootTime;
294 ALOGI("Boot is finished (%ld ms)", long(ns2ms(duration)) );
295 mBootFinished = true;
296
297 // wait patiently for the window manager death
298 const String16 name("window");
299 sp<IBinder> window(defaultServiceManager()->getService(name));
300 if (window != 0) {
301 window->linkToDeath(static_cast<IBinder::DeathRecipient*>(this));
302 }
303
304 // stop boot animation
305 // formerly we would just kill the process, but we now ask it to exit so it
306 // can choose where to stop the animation.
307 property_set("service.bootanim.exit", "1");
308
309 const int LOGTAG_SF_STOP_BOOTANIM = 60110;
310 LOG_EVENT_LONG(LOGTAG_SF_STOP_BOOTANIM,
311 ns2ms(systemTime(SYSTEM_TIME_MONOTONIC)));
312}
313
314void SurfaceFlinger::deleteTextureAsync(uint32_t texture) {
315 class MessageDestroyGLTexture : public MessageBase {
316 RenderEngine& engine;
317 uint32_t texture;
318 public:
319 MessageDestroyGLTexture(RenderEngine& engine, uint32_t texture)
320 : engine(engine), texture(texture) {
321 }
322 virtual bool handler() {
323 engine.deleteTextures(1, &texture);
324 return true;
325 }
326 };
327 postMessageAsync(new MessageDestroyGLTexture(getRenderEngine(), texture));
328}
329
330class DispSyncSource : public VSyncSource, private DispSync::Callback {
331public:
332 DispSyncSource(DispSync* dispSync, nsecs_t phaseOffset, bool traceVsync,
Dan Stozaf34b9be2016-04-05 16:45:26 -0700333 const char* name) :
334 mName(name),
Dan Stoza9e56aa02015-11-02 13:00:03 -0800335 mValue(0),
336 mTraceVsync(traceVsync),
Dan Stozaf34b9be2016-04-05 16:45:26 -0700337 mVsyncOnLabel(String8::format("VsyncOn-%s", name)),
338 mVsyncEventLabel(String8::format("VSYNC-%s", name)),
Dan Stoza9e56aa02015-11-02 13:00:03 -0800339 mDispSync(dispSync),
340 mCallbackMutex(),
341 mCallback(),
342 mVsyncMutex(),
343 mPhaseOffset(phaseOffset),
344 mEnabled(false) {}
345
346 virtual ~DispSyncSource() {}
347
348 virtual void setVSyncEnabled(bool enable) {
349 Mutex::Autolock lock(mVsyncMutex);
350 if (enable) {
Dan Stozaf34b9be2016-04-05 16:45:26 -0700351 status_t err = mDispSync->addEventListener(mName, mPhaseOffset,
Dan Stoza9e56aa02015-11-02 13:00:03 -0800352 static_cast<DispSync::Callback*>(this));
353 if (err != NO_ERROR) {
354 ALOGE("error registering vsync callback: %s (%d)",
355 strerror(-err), err);
356 }
357 //ATRACE_INT(mVsyncOnLabel.string(), 1);
358 } else {
359 status_t err = mDispSync->removeEventListener(
360 static_cast<DispSync::Callback*>(this));
361 if (err != NO_ERROR) {
362 ALOGE("error unregistering vsync callback: %s (%d)",
363 strerror(-err), err);
364 }
365 //ATRACE_INT(mVsyncOnLabel.string(), 0);
366 }
367 mEnabled = enable;
368 }
369
370 virtual void setCallback(const sp<VSyncSource::Callback>& callback) {
371 Mutex::Autolock lock(mCallbackMutex);
372 mCallback = callback;
373 }
374
375 virtual void setPhaseOffset(nsecs_t phaseOffset) {
376 Mutex::Autolock lock(mVsyncMutex);
377
378 // Normalize phaseOffset to [0, period)
379 auto period = mDispSync->getPeriod();
380 phaseOffset %= period;
381 if (phaseOffset < 0) {
382 // If we're here, then phaseOffset is in (-period, 0). After this
383 // operation, it will be in (0, period)
384 phaseOffset += period;
385 }
386 mPhaseOffset = phaseOffset;
387
388 // If we're not enabled, we don't need to mess with the listeners
389 if (!mEnabled) {
390 return;
391 }
392
393 // Remove the listener with the old offset
394 status_t err = mDispSync->removeEventListener(
395 static_cast<DispSync::Callback*>(this));
396 if (err != NO_ERROR) {
397 ALOGE("error unregistering vsync callback: %s (%d)",
398 strerror(-err), err);
399 }
400
401 // Add a listener with the new offset
Dan Stozaf34b9be2016-04-05 16:45:26 -0700402 err = mDispSync->addEventListener(mName, mPhaseOffset,
Dan Stoza9e56aa02015-11-02 13:00:03 -0800403 static_cast<DispSync::Callback*>(this));
404 if (err != NO_ERROR) {
405 ALOGE("error registering vsync callback: %s (%d)",
406 strerror(-err), err);
407 }
408 }
409
410private:
411 virtual void onDispSyncEvent(nsecs_t when) {
412 sp<VSyncSource::Callback> callback;
413 {
414 Mutex::Autolock lock(mCallbackMutex);
415 callback = mCallback;
416
417 if (mTraceVsync) {
418 mValue = (mValue + 1) % 2;
419 ATRACE_INT(mVsyncEventLabel.string(), mValue);
420 }
421 }
422
423 if (callback != NULL) {
424 callback->onVSyncEvent(when);
425 }
426 }
427
Dan Stozaf34b9be2016-04-05 16:45:26 -0700428 const char* const mName;
429
Dan Stoza9e56aa02015-11-02 13:00:03 -0800430 int mValue;
431
432 const bool mTraceVsync;
433 const String8 mVsyncOnLabel;
434 const String8 mVsyncEventLabel;
435
436 DispSync* mDispSync;
437
438 Mutex mCallbackMutex; // Protects the following
439 sp<VSyncSource::Callback> mCallback;
440
441 Mutex mVsyncMutex; // Protects the following
442 nsecs_t mPhaseOffset;
443 bool mEnabled;
444};
445
446void SurfaceFlinger::init() {
447 ALOGI( "SurfaceFlinger's main thread ready to run. "
448 "Initializing graphics H/W...");
449
450 Mutex::Autolock _l(mStateLock);
451
452 // initialize EGL for the default display
453 mEGLDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY);
454 eglInitialize(mEGLDisplay, NULL, NULL);
455
456 // start the EventThread
457 sp<VSyncSource> vsyncSrc = new DispSyncSource(&mPrimaryDispSync,
458 vsyncPhaseOffsetNs, true, "app");
Dan Stozaf34b9be2016-04-05 16:45:26 -0700459 mEventThread = new EventThread(vsyncSrc, *this);
Dan Stoza9e56aa02015-11-02 13:00:03 -0800460 sp<VSyncSource> sfVsyncSrc = new DispSyncSource(&mPrimaryDispSync,
461 sfVsyncPhaseOffsetNs, true, "sf");
Dan Stozaf34b9be2016-04-05 16:45:26 -0700462 mSFEventThread = new EventThread(sfVsyncSrc, *this);
Dan Stoza9e56aa02015-11-02 13:00:03 -0800463 mEventQueue.setEventThread(mSFEventThread);
464
465 // Initialize the H/W composer object. There may or may not be an
466 // actual hardware composer underneath.
467 mHwc = new HWComposer(this,
468 *static_cast<HWComposer::EventHandler *>(this));
469
470 // get a RenderEngine for the given display / config (can't fail)
471 mRenderEngine = RenderEngine::create(mEGLDisplay, mHwc->getVisualID());
472
473 // retrieve the EGL context that was selected/created
474 mEGLContext = mRenderEngine->getEGLContext();
475
476 LOG_ALWAYS_FATAL_IF(mEGLContext == EGL_NO_CONTEXT,
477 "couldn't create EGLContext");
478
479 // initialize our non-virtual displays
480 for (size_t i=0 ; i<DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES ; i++) {
481 DisplayDevice::DisplayType type((DisplayDevice::DisplayType)i);
482 // set-up the displays that are already connected
483 if (mHwc->isConnected(i) || type==DisplayDevice::DISPLAY_PRIMARY) {
484 // All non-virtual displays are currently considered secure.
485 bool isSecure = true;
486 createBuiltinDisplayLocked(type);
487 wp<IBinder> token = mBuiltinDisplays[i];
488
489 sp<IGraphicBufferProducer> producer;
490 sp<IGraphicBufferConsumer> consumer;
491 BufferQueue::createBufferQueue(&producer, &consumer,
492 new GraphicBufferAlloc());
493
494 sp<FramebufferSurface> fbs = new FramebufferSurface(*mHwc, i,
495 consumer);
496 int32_t hwcId = allocateHwcDisplayId(type);
497 sp<DisplayDevice> hw = new DisplayDevice(this,
498 type, hwcId, mHwc->getFormat(hwcId), isSecure, token,
499 fbs, producer,
500 mRenderEngine->getEGLConfig());
501 if (i > DisplayDevice::DISPLAY_PRIMARY) {
502 // FIXME: currently we don't get blank/unblank requests
503 // for displays other than the main display, so we always
504 // assume a connected display is unblanked.
505 ALOGD("marking display %zu as acquired/unblanked", i);
506 hw->setPowerMode(HWC_POWER_MODE_NORMAL);
507 }
508 mDisplays.add(token, hw);
509 }
510 }
511
512 // make the GLContext current so that we can create textures when creating Layers
513 // (which may happens before we render something)
514 getDefaultDisplayDevice()->makeCurrent(mEGLDisplay, mEGLContext);
515
516 mEventControlThread = new EventControlThread(this);
517 mEventControlThread->run("EventControl", PRIORITY_URGENT_DISPLAY);
518
519 // set a fake vsync period if there is no HWComposer
520 if (mHwc->initCheck() != NO_ERROR) {
521 mPrimaryDispSync.setPeriod(16666667);
522 }
523
524 // initialize our drawing state
525 mDrawingState = mCurrentState;
526
527 // set initial conditions (e.g. unblank default device)
528 initializeDisplays();
529
530 // start boot animation
531 startBootAnim();
532}
533
534int32_t SurfaceFlinger::allocateHwcDisplayId(DisplayDevice::DisplayType type) {
535 return (uint32_t(type) < DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES) ?
536 type : mHwc->allocateDisplayId();
537}
538
539void SurfaceFlinger::startBootAnim() {
540 // start boot animation
541 property_set("service.bootanim.exit", "0");
542 property_set("ctl.start", "bootanim");
543}
544
545size_t SurfaceFlinger::getMaxTextureSize() const {
546 return mRenderEngine->getMaxTextureSize();
547}
548
549size_t SurfaceFlinger::getMaxViewportDims() const {
550 return mRenderEngine->getMaxViewportDims();
551}
552
553// ----------------------------------------------------------------------------
554
555bool SurfaceFlinger::authenticateSurfaceTexture(
556 const sp<IGraphicBufferProducer>& bufferProducer) const {
557 Mutex::Autolock _l(mStateLock);
558 sp<IBinder> surfaceTextureBinder(IInterface::asBinder(bufferProducer));
559 return mGraphicBufferProducerList.indexOf(surfaceTextureBinder) >= 0;
560}
561
562status_t SurfaceFlinger::getDisplayConfigs(const sp<IBinder>& display,
563 Vector<DisplayInfo>* configs) {
564 if ((configs == NULL) || (display.get() == NULL)) {
565 return BAD_VALUE;
566 }
567
568 if (!display.get())
569 return NAME_NOT_FOUND;
570
571 int32_t type = NAME_NOT_FOUND;
572 for (int i=0 ; i<DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES ; i++) {
573 if (display == mBuiltinDisplays[i]) {
574 type = i;
575 break;
576 }
577 }
578
579 if (type < 0) {
580 return type;
581 }
582
583 // TODO: Not sure if display density should handled by SF any longer
584 class Density {
585 static int getDensityFromProperty(char const* propName) {
586 char property[PROPERTY_VALUE_MAX];
587 int density = 0;
588 if (property_get(propName, property, NULL) > 0) {
589 density = atoi(property);
590 }
591 return density;
592 }
593 public:
594 static int getEmuDensity() {
595 return getDensityFromProperty("qemu.sf.lcd_density"); }
596 static int getBuildDensity() {
597 return getDensityFromProperty("ro.sf.lcd_density"); }
598 };
599
600 configs->clear();
601
602 const Vector<HWComposer::DisplayConfig>& hwConfigs =
603 getHwComposer().getConfigs(type);
604 for (size_t c = 0; c < hwConfigs.size(); ++c) {
605 const HWComposer::DisplayConfig& hwConfig = hwConfigs[c];
606 DisplayInfo info = DisplayInfo();
607
608 float xdpi = hwConfig.xdpi;
609 float ydpi = hwConfig.ydpi;
610
611 if (type == DisplayDevice::DISPLAY_PRIMARY) {
612 // The density of the device is provided by a build property
613 float density = Density::getBuildDensity() / 160.0f;
614 if (density == 0) {
615 // the build doesn't provide a density -- this is wrong!
616 // use xdpi instead
617 ALOGE("ro.sf.lcd_density must be defined as a build property");
618 density = xdpi / 160.0f;
619 }
620 if (Density::getEmuDensity()) {
621 // if "qemu.sf.lcd_density" is specified, it overrides everything
622 xdpi = ydpi = density = Density::getEmuDensity();
623 density /= 160.0f;
624 }
625 info.density = density;
626
627 // TODO: this needs to go away (currently needed only by webkit)
628 sp<const DisplayDevice> hw(getDefaultDisplayDevice());
629 info.orientation = hw->getOrientation();
630 } else {
631 // TODO: where should this value come from?
632 static const int TV_DENSITY = 213;
633 info.density = TV_DENSITY / 160.0f;
634 info.orientation = 0;
635 }
636
637 info.w = hwConfig.width;
638 info.h = hwConfig.height;
639 info.xdpi = xdpi;
640 info.ydpi = ydpi;
641 info.fps = float(1e9 / hwConfig.refresh);
642 info.appVsyncOffset = VSYNC_EVENT_PHASE_OFFSET_NS;
643 info.colorTransform = hwConfig.colorTransform;
644
645 // This is how far in advance a buffer must be queued for
646 // presentation at a given time. If you want a buffer to appear
647 // on the screen at time N, you must submit the buffer before
648 // (N - presentationDeadline).
649 //
650 // Normally it's one full refresh period (to give SF a chance to
651 // latch the buffer), but this can be reduced by configuring a
652 // DispSync offset. Any additional delays introduced by the hardware
653 // composer or panel must be accounted for here.
654 //
655 // We add an additional 1ms to allow for processing time and
656 // differences between the ideal and actual refresh rate.
657 info.presentationDeadline =
658 hwConfig.refresh - SF_VSYNC_EVENT_PHASE_OFFSET_NS + 1000000;
659
660 // All non-virtual displays are currently considered secure.
661 info.secure = true;
662
663 configs->push_back(info);
664 }
665
666 return NO_ERROR;
667}
668
669status_t SurfaceFlinger::getDisplayStats(const sp<IBinder>& /* display */,
670 DisplayStatInfo* stats) {
671 if (stats == NULL) {
672 return BAD_VALUE;
673 }
674
675 // FIXME for now we always return stats for the primary display
676 memset(stats, 0, sizeof(*stats));
677 stats->vsyncTime = mPrimaryDispSync.computeNextRefresh(0);
678 stats->vsyncPeriod = mPrimaryDispSync.getPeriod();
679 return NO_ERROR;
680}
681
682int SurfaceFlinger::getActiveConfig(const sp<IBinder>& display) {
683 sp<DisplayDevice> device(getDisplayDevice(display));
684 if (device != NULL) {
685 return device->getActiveConfig();
686 }
687 return BAD_VALUE;
688}
689
690void SurfaceFlinger::setActiveConfigInternal(const sp<DisplayDevice>& hw, int mode) {
691 ALOGD("Set active config mode=%d, type=%d flinger=%p", mode, hw->getDisplayType(),
692 this);
693 int32_t type = hw->getDisplayType();
694 int currentMode = hw->getActiveConfig();
695
696 if (mode == currentMode) {
697 ALOGD("Screen type=%d is already mode=%d", hw->getDisplayType(), mode);
698 return;
699 }
700
701 if (type >= DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES) {
702 ALOGW("Trying to set config for virtual display");
703 return;
704 }
705
706 hw->setActiveConfig(mode);
707 getHwComposer().setActiveConfig(type, mode);
708}
709
710status_t SurfaceFlinger::setActiveConfig(const sp<IBinder>& display, int mode) {
711 class MessageSetActiveConfig: public MessageBase {
712 SurfaceFlinger& mFlinger;
713 sp<IBinder> mDisplay;
714 int mMode;
715 public:
716 MessageSetActiveConfig(SurfaceFlinger& flinger, const sp<IBinder>& disp,
717 int mode) :
718 mFlinger(flinger), mDisplay(disp) { mMode = mode; }
719 virtual bool handler() {
720 Vector<DisplayInfo> configs;
721 mFlinger.getDisplayConfigs(mDisplay, &configs);
722 if (mMode < 0 || mMode >= static_cast<int>(configs.size())) {
723 ALOGE("Attempt to set active config = %d for display with %zu configs",
724 mMode, configs.size());
725 }
726 sp<DisplayDevice> hw(mFlinger.getDisplayDevice(mDisplay));
727 if (hw == NULL) {
728 ALOGE("Attempt to set active config = %d for null display %p",
729 mMode, mDisplay.get());
730 } else if (hw->getDisplayType() >= DisplayDevice::DISPLAY_VIRTUAL) {
731 ALOGW("Attempt to set active config = %d for virtual display",
732 mMode);
733 } else {
734 mFlinger.setActiveConfigInternal(hw, mMode);
735 }
736 return true;
737 }
738 };
739 sp<MessageBase> msg = new MessageSetActiveConfig(*this, display, mode);
740 postMessageSync(msg);
741 return NO_ERROR;
742}
743
744status_t SurfaceFlinger::clearAnimationFrameStats() {
745 Mutex::Autolock _l(mStateLock);
746 mAnimFrameTracker.clearStats();
747 return NO_ERROR;
748}
749
750status_t SurfaceFlinger::getAnimationFrameStats(FrameStats* outStats) const {
751 Mutex::Autolock _l(mStateLock);
752 mAnimFrameTracker.getStats(outStats);
753 return NO_ERROR;
754}
755
Dan Stozac4f471e2016-03-24 09:31:08 -0700756status_t SurfaceFlinger::getHdrCapabilities(const sp<IBinder>& /*display*/,
757 HdrCapabilities* outCapabilities) const {
758 // HWC1 does not provide HDR capabilities
759 *outCapabilities = HdrCapabilities();
760 return NO_ERROR;
761}
762
Dan Stoza9e56aa02015-11-02 13:00:03 -0800763// ----------------------------------------------------------------------------
764
765sp<IDisplayEventConnection> SurfaceFlinger::createDisplayEventConnection() {
766 return mEventThread->createEventConnection();
767}
768
769// ----------------------------------------------------------------------------
770
771void SurfaceFlinger::waitForEvent() {
772 mEventQueue.waitMessage();
773}
774
775void SurfaceFlinger::signalTransaction() {
776 mEventQueue.invalidate();
777}
778
779void SurfaceFlinger::signalLayerUpdate() {
780 mEventQueue.invalidate();
781}
782
783void SurfaceFlinger::signalRefresh() {
784 mEventQueue.refresh();
785}
786
787status_t SurfaceFlinger::postMessageAsync(const sp<MessageBase>& msg,
788 nsecs_t reltime, uint32_t /* flags */) {
789 return mEventQueue.postMessage(msg, reltime);
790}
791
792status_t SurfaceFlinger::postMessageSync(const sp<MessageBase>& msg,
793 nsecs_t reltime, uint32_t /* flags */) {
794 status_t res = mEventQueue.postMessage(msg, reltime);
795 if (res == NO_ERROR) {
796 msg->wait();
797 }
798 return res;
799}
800
801void SurfaceFlinger::run() {
802 do {
803 waitForEvent();
804 } while (true);
805}
806
807void SurfaceFlinger::enableHardwareVsync() {
808 Mutex::Autolock _l(mHWVsyncLock);
809 if (!mPrimaryHWVsyncEnabled && mHWVsyncAvailable) {
810 mPrimaryDispSync.beginResync();
811 //eventControl(HWC_DISPLAY_PRIMARY, SurfaceFlinger::EVENT_VSYNC, true);
812 mEventControlThread->setVsyncEnabled(true);
813 mPrimaryHWVsyncEnabled = true;
814 }
815}
816
817void SurfaceFlinger::resyncToHardwareVsync(bool makeAvailable) {
818 Mutex::Autolock _l(mHWVsyncLock);
819
820 if (makeAvailable) {
821 mHWVsyncAvailable = true;
822 } else if (!mHWVsyncAvailable) {
823 ALOGE("resyncToHardwareVsync called when HW vsync unavailable");
824 return;
825 }
826
827 const nsecs_t period =
828 getHwComposer().getRefreshPeriod(HWC_DISPLAY_PRIMARY);
829
830 mPrimaryDispSync.reset();
831 mPrimaryDispSync.setPeriod(period);
832
833 if (!mPrimaryHWVsyncEnabled) {
834 mPrimaryDispSync.beginResync();
835 //eventControl(HWC_DISPLAY_PRIMARY, SurfaceFlinger::EVENT_VSYNC, true);
836 mEventControlThread->setVsyncEnabled(true);
837 mPrimaryHWVsyncEnabled = true;
838 }
839}
840
841void SurfaceFlinger::disableHardwareVsync(bool makeUnavailable) {
842 Mutex::Autolock _l(mHWVsyncLock);
843 if (mPrimaryHWVsyncEnabled) {
844 //eventControl(HWC_DISPLAY_PRIMARY, SurfaceFlinger::EVENT_VSYNC, false);
845 mEventControlThread->setVsyncEnabled(false);
846 mPrimaryDispSync.endResync();
847 mPrimaryHWVsyncEnabled = false;
848 }
849 if (makeUnavailable) {
850 mHWVsyncAvailable = false;
851 }
852}
853
Dan Stozaf34b9be2016-04-05 16:45:26 -0700854void SurfaceFlinger::resyncWithRateLimit() {
855 static constexpr nsecs_t kIgnoreDelay = ms2ns(500);
856 if (systemTime() - mLastSwapTime > kIgnoreDelay) {
857 resyncToHardwareVsync(true);
858 }
859}
860
Dan Stoza9e56aa02015-11-02 13:00:03 -0800861void SurfaceFlinger::onVSyncReceived(int type, nsecs_t timestamp) {
862 bool needsHwVsync = false;
863
864 { // Scope for the lock
865 Mutex::Autolock _l(mHWVsyncLock);
866 if (type == 0 && mPrimaryHWVsyncEnabled) {
867 needsHwVsync = mPrimaryDispSync.addResyncSample(timestamp);
868 }
869 }
870
871 if (needsHwVsync) {
872 enableHardwareVsync();
873 } else {
874 disableHardwareVsync(false);
875 }
876}
877
878void SurfaceFlinger::onHotplugReceived(int type, bool connected) {
879 if (mEventThread == NULL) {
880 // This is a temporary workaround for b/7145521. A non-null pointer
881 // does not mean EventThread has finished initializing, so this
882 // is not a correct fix.
883 ALOGW("WARNING: EventThread not started, ignoring hotplug");
884 return;
885 }
886
887 if (uint32_t(type) < DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES) {
888 Mutex::Autolock _l(mStateLock);
889 if (connected) {
890 createBuiltinDisplayLocked((DisplayDevice::DisplayType)type);
891 } else {
892 mCurrentState.displays.removeItem(mBuiltinDisplays[type]);
893 mBuiltinDisplays[type].clear();
894 }
895 setTransactionFlags(eDisplayTransactionNeeded);
896
897 // Defer EventThread notification until SF has updated mDisplays.
898 }
899}
900
901void SurfaceFlinger::eventControl(int disp, int event, int enabled) {
902 ATRACE_CALL();
903 getHwComposer().eventControl(disp, event, enabled);
904}
905
906void SurfaceFlinger::onMessageReceived(int32_t what) {
907 ATRACE_CALL();
908 switch (what) {
909 case MessageQueue::TRANSACTION: {
910 handleMessageTransaction();
911 break;
912 }
913 case MessageQueue::INVALIDATE: {
914 bool refreshNeeded = handleMessageTransaction();
915 refreshNeeded |= handleMessageInvalidate();
916 refreshNeeded |= mRepaintEverything;
917 if (refreshNeeded) {
918 // Signal a refresh if a transaction modified the window state,
919 // a new buffer was latched, or if HWC has requested a full
920 // repaint
921 signalRefresh();
922 }
923 break;
924 }
925 case MessageQueue::REFRESH: {
926 handleMessageRefresh();
927 break;
928 }
929 }
930}
931
932bool SurfaceFlinger::handleMessageTransaction() {
933 uint32_t transactionFlags = peekTransactionFlags(eTransactionMask);
934 if (transactionFlags) {
935 handleTransaction(transactionFlags);
936 return true;
937 }
938 return false;
939}
940
941bool SurfaceFlinger::handleMessageInvalidate() {
942 ATRACE_CALL();
943 return handlePageFlip();
944}
945
946void SurfaceFlinger::handleMessageRefresh() {
947 ATRACE_CALL();
948
Pablo Ceballos69a1a382016-03-30 15:28:05 -0700949#ifdef ENABLE_FENCE_TRACKING
Pablo Ceballos40845df2016-01-25 17:41:15 -0800950 nsecs_t refreshStartTime = systemTime(SYSTEM_TIME_MONOTONIC);
Pablo Ceballos69a1a382016-03-30 15:28:05 -0700951#else
952 nsecs_t refreshStartTime = 0;
953#endif
Dan Stoza9e56aa02015-11-02 13:00:03 -0800954 static nsecs_t previousExpectedPresent = 0;
955 nsecs_t expectedPresent = mPrimaryDispSync.computeNextRefresh(0);
956 static bool previousFrameMissed = false;
957 bool frameMissed = (expectedPresent == previousExpectedPresent);
958 if (frameMissed != previousFrameMissed) {
959 ATRACE_INT("FrameMissed", static_cast<int>(frameMissed));
960 }
961 previousFrameMissed = frameMissed;
962
963 if (CC_UNLIKELY(mDropMissedFrames && frameMissed)) {
964 // Latch buffers, but don't send anything to HWC, then signal another
965 // wakeup for the next vsync
966 preComposition();
967 repaintEverything();
968 } else {
969 preComposition();
970 rebuildLayerStacks();
971 setUpHWComposer();
972 doDebugFlashRegions();
973 doComposition();
Pablo Ceballos40845df2016-01-25 17:41:15 -0800974 postComposition(refreshStartTime);
Dan Stoza9e56aa02015-11-02 13:00:03 -0800975 }
976
977 previousExpectedPresent = mPrimaryDispSync.computeNextRefresh(0);
978}
979
980void SurfaceFlinger::doDebugFlashRegions()
981{
982 // is debugging enabled
983 if (CC_LIKELY(!mDebugRegion))
984 return;
985
986 const bool repaintEverything = mRepaintEverything;
987 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
988 const sp<DisplayDevice>& hw(mDisplays[dpy]);
989 if (hw->isDisplayOn()) {
990 // transform the dirty region into this screen's coordinate space
991 const Region dirtyRegion(hw->getDirtyRegion(repaintEverything));
992 if (!dirtyRegion.isEmpty()) {
993 // redraw the whole screen
994 doComposeSurfaces(hw, Region(hw->bounds()));
995
996 // and draw the dirty region
997 const int32_t height = hw->getHeight();
998 RenderEngine& engine(getRenderEngine());
999 engine.fillRegionWithColor(dirtyRegion, height, 1, 0, 1, 1);
1000
1001 hw->compositionComplete();
1002 hw->swapBuffers(getHwComposer());
1003 }
1004 }
1005 }
1006
1007 postFramebuffer();
1008
1009 if (mDebugRegion > 1) {
1010 usleep(mDebugRegion * 1000);
1011 }
1012
1013 HWComposer& hwc(getHwComposer());
1014 if (hwc.initCheck() == NO_ERROR) {
1015 status_t err = hwc.prepare();
1016 ALOGE_IF(err, "HWComposer::prepare failed (%s)", strerror(-err));
1017 }
1018}
1019
1020void SurfaceFlinger::preComposition()
1021{
1022 bool needExtraInvalidate = false;
1023 const LayerVector& layers(mDrawingState.layersSortedByZ);
1024 const size_t count = layers.size();
1025 for (size_t i=0 ; i<count ; i++) {
1026 if (layers[i]->onPreComposition()) {
1027 needExtraInvalidate = true;
1028 }
1029 }
1030 if (needExtraInvalidate) {
1031 signalLayerUpdate();
1032 }
1033}
1034
Pablo Ceballos69a1a382016-03-30 15:28:05 -07001035#ifdef ENABLE_FENCE_TRACKING
Pablo Ceballos40845df2016-01-25 17:41:15 -08001036void SurfaceFlinger::postComposition(nsecs_t refreshStartTime)
Pablo Ceballos69a1a382016-03-30 15:28:05 -07001037#else
1038void SurfaceFlinger::postComposition(nsecs_t /*refreshStartTime*/)
1039#endif
Dan Stoza9e56aa02015-11-02 13:00:03 -08001040{
1041 const LayerVector& layers(mDrawingState.layersSortedByZ);
1042 const size_t count = layers.size();
1043 for (size_t i=0 ; i<count ; i++) {
1044 layers[i]->onPostComposition();
1045 }
1046
1047 const HWComposer& hwc = getHwComposer();
1048 sp<Fence> presentFence = hwc.getDisplayFence(HWC_DISPLAY_PRIMARY);
1049
1050 if (presentFence->isValid()) {
1051 if (mPrimaryDispSync.addPresentFence(presentFence)) {
1052 enableHardwareVsync();
1053 } else {
1054 disableHardwareVsync(false);
1055 }
1056 }
1057
1058 const sp<const DisplayDevice> hw(getDefaultDisplayDevice());
1059 if (kIgnorePresentFences) {
1060 if (hw->isDisplayOn()) {
1061 enableHardwareVsync();
1062 }
1063 }
1064
Pablo Ceballos69a1a382016-03-30 15:28:05 -07001065#ifdef ENABLE_FENCE_TRACKING
Pablo Ceballos40845df2016-01-25 17:41:15 -08001066 mFenceTracker.addFrame(refreshStartTime, presentFence,
1067 hw->getVisibleLayersSortedByZ(), hw->getClientTargetAcquireFence());
Pablo Ceballos69a1a382016-03-30 15:28:05 -07001068#endif
Pablo Ceballos40845df2016-01-25 17:41:15 -08001069
Dan Stoza9e56aa02015-11-02 13:00:03 -08001070 if (mAnimCompositionPending) {
1071 mAnimCompositionPending = false;
1072
1073 if (presentFence->isValid()) {
1074 mAnimFrameTracker.setActualPresentFence(presentFence);
1075 } else {
1076 // The HWC doesn't support present fences, so use the refresh
1077 // timestamp instead.
1078 nsecs_t presentTime = hwc.getRefreshTimestamp(HWC_DISPLAY_PRIMARY);
1079 mAnimFrameTracker.setActualPresentTime(presentTime);
1080 }
1081 mAnimFrameTracker.advanceFrame();
1082 }
1083
1084 if (hw->getPowerMode() == HWC_POWER_MODE_OFF) {
1085 return;
1086 }
1087
1088 nsecs_t currentTime = systemTime();
1089 if (mHasPoweredOff) {
1090 mHasPoweredOff = false;
1091 } else {
1092 nsecs_t period = mPrimaryDispSync.getPeriod();
1093 nsecs_t elapsedTime = currentTime - mLastSwapTime;
1094 size_t numPeriods = static_cast<size_t>(elapsedTime / period);
1095 if (numPeriods < NUM_BUCKETS - 1) {
1096 mFrameBuckets[numPeriods] += elapsedTime;
1097 } else {
1098 mFrameBuckets[NUM_BUCKETS - 1] += elapsedTime;
1099 }
1100 mTotalTime += elapsedTime;
1101 }
1102 mLastSwapTime = currentTime;
1103}
1104
1105void SurfaceFlinger::rebuildLayerStacks() {
1106 // rebuild the visible layer list per screen
1107 if (CC_UNLIKELY(mVisibleRegionsDirty)) {
1108 ATRACE_CALL();
1109 mVisibleRegionsDirty = false;
1110 invalidateHwcGeometry();
1111
1112 const LayerVector& layers(mDrawingState.layersSortedByZ);
1113 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1114 Region opaqueRegion;
1115 Region dirtyRegion;
1116 Vector< sp<Layer> > layersSortedByZ;
1117 const sp<DisplayDevice>& hw(mDisplays[dpy]);
1118 const Transform& tr(hw->getTransform());
1119 const Rect bounds(hw->getBounds());
1120 if (hw->isDisplayOn()) {
1121 SurfaceFlinger::computeVisibleRegions(layers,
1122 hw->getLayerStack(), dirtyRegion, opaqueRegion);
1123
1124 const size_t count = layers.size();
1125 for (size_t i=0 ; i<count ; i++) {
1126 const sp<Layer>& layer(layers[i]);
1127 const Layer::State& s(layer->getDrawingState());
1128 if (s.layerStack == hw->getLayerStack()) {
1129 Region drawRegion(tr.transform(
1130 layer->visibleNonTransparentRegion));
1131 drawRegion.andSelf(bounds);
1132 if (!drawRegion.isEmpty()) {
1133 layersSortedByZ.add(layer);
1134 }
1135 }
1136 }
1137 }
1138 hw->setVisibleLayersSortedByZ(layersSortedByZ);
1139 hw->undefinedRegion.set(bounds);
1140 hw->undefinedRegion.subtractSelf(tr.transform(opaqueRegion));
1141 hw->dirtyRegion.orSelf(dirtyRegion);
1142 }
1143 }
1144}
1145
1146void SurfaceFlinger::setUpHWComposer() {
1147 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1148 bool dirty = !mDisplays[dpy]->getDirtyRegion(false).isEmpty();
1149 bool empty = mDisplays[dpy]->getVisibleLayersSortedByZ().size() == 0;
1150 bool wasEmpty = !mDisplays[dpy]->lastCompositionHadVisibleLayers;
1151
1152 // If nothing has changed (!dirty), don't recompose.
1153 // If something changed, but we don't currently have any visible layers,
1154 // and didn't when we last did a composition, then skip it this time.
1155 // The second rule does two things:
1156 // - When all layers are removed from a display, we'll emit one black
1157 // frame, then nothing more until we get new layers.
1158 // - When a display is created with a private layer stack, we won't
1159 // emit any black frames until a layer is added to the layer stack.
1160 bool mustRecompose = dirty && !(empty && wasEmpty);
1161
1162 ALOGV_IF(mDisplays[dpy]->getDisplayType() == DisplayDevice::DISPLAY_VIRTUAL,
1163 "dpy[%zu]: %s composition (%sdirty %sempty %swasEmpty)", dpy,
1164 mustRecompose ? "doing" : "skipping",
1165 dirty ? "+" : "-",
1166 empty ? "+" : "-",
1167 wasEmpty ? "+" : "-");
1168
1169 mDisplays[dpy]->beginFrame(mustRecompose);
1170
1171 if (mustRecompose) {
1172 mDisplays[dpy]->lastCompositionHadVisibleLayers = !empty;
1173 }
1174 }
1175
1176 HWComposer& hwc(getHwComposer());
1177 if (hwc.initCheck() == NO_ERROR) {
1178 // build the h/w work list
1179 if (CC_UNLIKELY(mHwWorkListDirty)) {
1180 mHwWorkListDirty = false;
1181 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1182 sp<const DisplayDevice> hw(mDisplays[dpy]);
1183 const int32_t id = hw->getHwcDisplayId();
1184 if (id >= 0) {
1185 const Vector< sp<Layer> >& currentLayers(
1186 hw->getVisibleLayersSortedByZ());
1187 const size_t count = currentLayers.size();
1188 if (hwc.createWorkList(id, count) == NO_ERROR) {
1189 HWComposer::LayerListIterator cur = hwc.begin(id);
1190 const HWComposer::LayerListIterator end = hwc.end(id);
1191 for (size_t i=0 ; cur!=end && i<count ; ++i, ++cur) {
1192 const sp<Layer>& layer(currentLayers[i]);
1193 layer->setGeometry(hw, *cur);
1194 if (mDebugDisableHWC || mDebugRegion || mDaltonize || mHasColorMatrix) {
1195 cur->setSkip(true);
1196 }
1197 }
1198 }
1199 }
1200 }
1201 }
1202
1203 // set the per-frame data
1204 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1205 sp<const DisplayDevice> hw(mDisplays[dpy]);
1206 const int32_t id = hw->getHwcDisplayId();
1207 if (id >= 0) {
1208 const Vector< sp<Layer> >& currentLayers(
1209 hw->getVisibleLayersSortedByZ());
1210 const size_t count = currentLayers.size();
1211 HWComposer::LayerListIterator cur = hwc.begin(id);
1212 const HWComposer::LayerListIterator end = hwc.end(id);
1213 for (size_t i=0 ; cur!=end && i<count ; ++i, ++cur) {
1214 /*
1215 * update the per-frame h/w composer data for each layer
1216 * and build the transparent region of the FB
1217 */
1218 const sp<Layer>& layer(currentLayers[i]);
1219 layer->setPerFrameData(hw, *cur);
1220 }
1221 }
1222 }
1223
1224 // If possible, attempt to use the cursor overlay on each display.
1225 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1226 sp<const DisplayDevice> hw(mDisplays[dpy]);
1227 const int32_t id = hw->getHwcDisplayId();
1228 if (id >= 0) {
1229 const Vector< sp<Layer> >& currentLayers(
1230 hw->getVisibleLayersSortedByZ());
1231 const size_t count = currentLayers.size();
1232 HWComposer::LayerListIterator cur = hwc.begin(id);
1233 const HWComposer::LayerListIterator end = hwc.end(id);
1234 for (size_t i=0 ; cur!=end && i<count ; ++i, ++cur) {
1235 const sp<Layer>& layer(currentLayers[i]);
1236 if (layer->isPotentialCursor()) {
1237 cur->setIsCursorLayerHint();
1238 break;
1239 }
1240 }
1241 }
1242 }
1243
1244 status_t err = hwc.prepare();
1245 ALOGE_IF(err, "HWComposer::prepare failed (%s)", strerror(-err));
1246
1247 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1248 sp<const DisplayDevice> hw(mDisplays[dpy]);
1249 hw->prepareFrame(hwc);
1250 }
1251 }
1252}
1253
1254void SurfaceFlinger::doComposition() {
1255 ATRACE_CALL();
1256 const bool repaintEverything = android_atomic_and(0, &mRepaintEverything);
1257 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1258 const sp<DisplayDevice>& hw(mDisplays[dpy]);
1259 if (hw->isDisplayOn()) {
1260 // transform the dirty region into this screen's coordinate space
1261 const Region dirtyRegion(hw->getDirtyRegion(repaintEverything));
1262
1263 // repaint the framebuffer (if needed)
1264 doDisplayComposition(hw, dirtyRegion);
1265
1266 hw->dirtyRegion.clear();
1267 hw->flip(hw->swapRegion);
1268 hw->swapRegion.clear();
1269 }
1270 // inform the h/w that we're done compositing
1271 hw->compositionComplete();
1272 }
1273 postFramebuffer();
1274}
1275
1276void SurfaceFlinger::postFramebuffer()
1277{
1278 ATRACE_CALL();
1279
1280 const nsecs_t now = systemTime();
1281 mDebugInSwapBuffers = now;
1282
1283 HWComposer& hwc(getHwComposer());
1284 if (hwc.initCheck() == NO_ERROR) {
1285 if (!hwc.supportsFramebufferTarget()) {
1286 // EGL spec says:
1287 // "surface must be bound to the calling thread's current context,
1288 // for the current rendering API."
1289 getDefaultDisplayDevice()->makeCurrent(mEGLDisplay, mEGLContext);
1290 }
1291 hwc.commit();
1292 }
1293
1294 // make the default display current because the VirtualDisplayDevice code cannot
1295 // deal with dequeueBuffer() being called outside of the composition loop; however
1296 // the code below can call glFlush() which is allowed (and does in some case) call
1297 // dequeueBuffer().
1298 getDefaultDisplayDevice()->makeCurrent(mEGLDisplay, mEGLContext);
1299
1300 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1301 sp<const DisplayDevice> hw(mDisplays[dpy]);
1302 const Vector< sp<Layer> >& currentLayers(hw->getVisibleLayersSortedByZ());
1303 hw->onSwapBuffersCompleted(hwc);
1304 const size_t count = currentLayers.size();
1305 int32_t id = hw->getHwcDisplayId();
1306 if (id >=0 && hwc.initCheck() == NO_ERROR) {
1307 HWComposer::LayerListIterator cur = hwc.begin(id);
1308 const HWComposer::LayerListIterator end = hwc.end(id);
1309 for (size_t i = 0; cur != end && i < count; ++i, ++cur) {
1310 currentLayers[i]->onLayerDisplayed(hw, &*cur);
1311 }
1312 } else {
1313 for (size_t i = 0; i < count; i++) {
1314 currentLayers[i]->onLayerDisplayed(hw, NULL);
1315 }
1316 }
1317 }
1318
1319 mLastSwapBufferTime = systemTime() - now;
1320 mDebugInSwapBuffers = 0;
1321
1322 uint32_t flipCount = getDefaultDisplayDevice()->getPageFlipCount();
1323 if (flipCount % LOG_FRAME_STATS_PERIOD == 0) {
1324 logFrameStats();
1325 }
1326}
1327
1328void SurfaceFlinger::handleTransaction(uint32_t transactionFlags)
1329{
1330 ATRACE_CALL();
1331
1332 // here we keep a copy of the drawing state (that is the state that's
1333 // going to be overwritten by handleTransactionLocked()) outside of
1334 // mStateLock so that the side-effects of the State assignment
1335 // don't happen with mStateLock held (which can cause deadlocks).
1336 State drawingState(mDrawingState);
1337
1338 Mutex::Autolock _l(mStateLock);
1339 const nsecs_t now = systemTime();
1340 mDebugInTransaction = now;
1341
1342 // Here we're guaranteed that some transaction flags are set
1343 // so we can call handleTransactionLocked() unconditionally.
1344 // We call getTransactionFlags(), which will also clear the flags,
1345 // with mStateLock held to guarantee that mCurrentState won't change
1346 // until the transaction is committed.
1347
1348 transactionFlags = getTransactionFlags(eTransactionMask);
1349 handleTransactionLocked(transactionFlags);
1350
1351 mLastTransactionTime = systemTime() - now;
1352 mDebugInTransaction = 0;
1353 invalidateHwcGeometry();
1354 // here the transaction has been committed
1355}
1356
1357void SurfaceFlinger::handleTransactionLocked(uint32_t transactionFlags)
1358{
1359 const LayerVector& currentLayers(mCurrentState.layersSortedByZ);
1360 const size_t count = currentLayers.size();
1361
1362 // Notify all layers of available frames
1363 for (size_t i = 0; i < count; ++i) {
1364 currentLayers[i]->notifyAvailableFrames();
1365 }
1366
1367 /*
1368 * Traversal of the children
1369 * (perform the transaction for each of them if needed)
1370 */
1371
1372 if (transactionFlags & eTraversalNeeded) {
1373 for (size_t i=0 ; i<count ; i++) {
1374 const sp<Layer>& layer(currentLayers[i]);
1375 uint32_t trFlags = layer->getTransactionFlags(eTransactionNeeded);
1376 if (!trFlags) continue;
1377
1378 const uint32_t flags = layer->doTransaction(0);
1379 if (flags & Layer::eVisibleRegion)
1380 mVisibleRegionsDirty = true;
1381 }
1382 }
1383
1384 /*
1385 * Perform display own transactions if needed
1386 */
1387
1388 if (transactionFlags & eDisplayTransactionNeeded) {
1389 // here we take advantage of Vector's copy-on-write semantics to
1390 // improve performance by skipping the transaction entirely when
1391 // know that the lists are identical
1392 const KeyedVector< wp<IBinder>, DisplayDeviceState>& curr(mCurrentState.displays);
1393 const KeyedVector< wp<IBinder>, DisplayDeviceState>& draw(mDrawingState.displays);
1394 if (!curr.isIdenticalTo(draw)) {
1395 mVisibleRegionsDirty = true;
1396 const size_t cc = curr.size();
1397 size_t dc = draw.size();
1398
1399 // find the displays that were removed
1400 // (ie: in drawing state but not in current state)
1401 // also handle displays that changed
1402 // (ie: displays that are in both lists)
1403 for (size_t i=0 ; i<dc ; i++) {
1404 const ssize_t j = curr.indexOfKey(draw.keyAt(i));
1405 if (j < 0) {
1406 // in drawing state but not in current state
1407 if (!draw[i].isMainDisplay()) {
1408 // Call makeCurrent() on the primary display so we can
1409 // be sure that nothing associated with this display
1410 // is current.
1411 const sp<const DisplayDevice> defaultDisplay(getDefaultDisplayDevice());
1412 defaultDisplay->makeCurrent(mEGLDisplay, mEGLContext);
1413 sp<DisplayDevice> hw(getDisplayDevice(draw.keyAt(i)));
1414 if (hw != NULL)
1415 hw->disconnect(getHwComposer());
1416 if (draw[i].type < DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES)
1417 mEventThread->onHotplugReceived(draw[i].type, false);
1418 mDisplays.removeItem(draw.keyAt(i));
1419 } else {
1420 ALOGW("trying to remove the main display");
1421 }
1422 } else {
1423 // this display is in both lists. see if something changed.
1424 const DisplayDeviceState& state(curr[j]);
1425 const wp<IBinder>& display(curr.keyAt(j));
1426 const sp<IBinder> state_binder = IInterface::asBinder(state.surface);
1427 const sp<IBinder> draw_binder = IInterface::asBinder(draw[i].surface);
1428 if (state_binder != draw_binder) {
1429 // changing the surface is like destroying and
1430 // recreating the DisplayDevice, so we just remove it
1431 // from the drawing state, so that it get re-added
1432 // below.
1433 sp<DisplayDevice> hw(getDisplayDevice(display));
1434 if (hw != NULL)
1435 hw->disconnect(getHwComposer());
1436 mDisplays.removeItem(display);
1437 mDrawingState.displays.removeItemsAt(i);
1438 dc--; i--;
1439 // at this point we must loop to the next item
1440 continue;
1441 }
1442
1443 const sp<DisplayDevice> disp(getDisplayDevice(display));
1444 if (disp != NULL) {
1445 if (state.layerStack != draw[i].layerStack) {
1446 disp->setLayerStack(state.layerStack);
1447 }
1448 if ((state.orientation != draw[i].orientation)
1449 || (state.viewport != draw[i].viewport)
1450 || (state.frame != draw[i].frame))
1451 {
1452 disp->setProjection(state.orientation,
1453 state.viewport, state.frame);
1454 }
1455 if (state.width != draw[i].width || state.height != draw[i].height) {
1456 disp->setDisplaySize(state.width, state.height);
1457 }
1458 }
1459 }
1460 }
1461
1462 // find displays that were added
1463 // (ie: in current state but not in drawing state)
1464 for (size_t i=0 ; i<cc ; i++) {
1465 if (draw.indexOfKey(curr.keyAt(i)) < 0) {
1466 const DisplayDeviceState& state(curr[i]);
1467
1468 sp<DisplaySurface> dispSurface;
1469 sp<IGraphicBufferProducer> producer;
1470 sp<IGraphicBufferProducer> bqProducer;
1471 sp<IGraphicBufferConsumer> bqConsumer;
1472 BufferQueue::createBufferQueue(&bqProducer, &bqConsumer,
1473 new GraphicBufferAlloc());
1474
1475 int32_t hwcDisplayId = -1;
1476 if (state.isVirtualDisplay()) {
1477 // Virtual displays without a surface are dormant:
1478 // they have external state (layer stack, projection,
1479 // etc.) but no internal state (i.e. a DisplayDevice).
1480 if (state.surface != NULL) {
1481
1482 int width = 0;
1483 int status = state.surface->query(
1484 NATIVE_WINDOW_WIDTH, &width);
1485 ALOGE_IF(status != NO_ERROR,
1486 "Unable to query width (%d)", status);
1487 int height = 0;
1488 status = state.surface->query(
1489 NATIVE_WINDOW_HEIGHT, &height);
1490 ALOGE_IF(status != NO_ERROR,
1491 "Unable to query height (%d)", status);
1492 if (MAX_VIRTUAL_DISPLAY_DIMENSION == 0 ||
1493 (width <= MAX_VIRTUAL_DISPLAY_DIMENSION &&
1494 height <= MAX_VIRTUAL_DISPLAY_DIMENSION)) {
1495 hwcDisplayId = allocateHwcDisplayId(state.type);
1496 }
1497
1498 sp<VirtualDisplaySurface> vds = new VirtualDisplaySurface(
1499 *mHwc, hwcDisplayId, state.surface,
1500 bqProducer, bqConsumer, state.displayName);
1501
1502 dispSurface = vds;
1503 producer = vds;
1504 }
1505 } else {
1506 ALOGE_IF(state.surface!=NULL,
1507 "adding a supported display, but rendering "
1508 "surface is provided (%p), ignoring it",
1509 state.surface.get());
1510 hwcDisplayId = allocateHwcDisplayId(state.type);
1511 // for supported (by hwc) displays we provide our
1512 // own rendering surface
1513 dispSurface = new FramebufferSurface(*mHwc, state.type,
1514 bqConsumer);
1515 producer = bqProducer;
1516 }
1517
1518 const wp<IBinder>& display(curr.keyAt(i));
1519 if (dispSurface != NULL) {
1520 sp<DisplayDevice> hw = new DisplayDevice(this,
1521 state.type, hwcDisplayId,
1522 mHwc->getFormat(hwcDisplayId), state.isSecure,
1523 display, dispSurface, producer,
1524 mRenderEngine->getEGLConfig());
1525 hw->setLayerStack(state.layerStack);
1526 hw->setProjection(state.orientation,
1527 state.viewport, state.frame);
1528 hw->setDisplayName(state.displayName);
1529 mDisplays.add(display, hw);
1530 if (state.isVirtualDisplay()) {
1531 if (hwcDisplayId >= 0) {
1532 mHwc->setVirtualDisplayProperties(hwcDisplayId,
1533 hw->getWidth(), hw->getHeight(),
1534 hw->getFormat());
1535 }
1536 } else {
1537 mEventThread->onHotplugReceived(state.type, true);
1538 }
1539 }
1540 }
1541 }
1542 }
1543 }
1544
1545 if (transactionFlags & (eTraversalNeeded|eDisplayTransactionNeeded)) {
1546 // The transform hint might have changed for some layers
1547 // (either because a display has changed, or because a layer
1548 // as changed).
1549 //
1550 // Walk through all the layers in currentLayers,
1551 // and update their transform hint.
1552 //
1553 // If a layer is visible only on a single display, then that
1554 // display is used to calculate the hint, otherwise we use the
1555 // default display.
1556 //
1557 // NOTE: we do this here, rather than in rebuildLayerStacks() so that
1558 // the hint is set before we acquire a buffer from the surface texture.
1559 //
1560 // NOTE: layer transactions have taken place already, so we use their
1561 // drawing state. However, SurfaceFlinger's own transaction has not
1562 // happened yet, so we must use the current state layer list
1563 // (soon to become the drawing state list).
1564 //
1565 sp<const DisplayDevice> disp;
1566 uint32_t currentlayerStack = 0;
1567 for (size_t i=0; i<count; i++) {
1568 // NOTE: we rely on the fact that layers are sorted by
1569 // layerStack first (so we don't have to traverse the list
1570 // of displays for every layer).
1571 const sp<Layer>& layer(currentLayers[i]);
1572 uint32_t layerStack = layer->getDrawingState().layerStack;
1573 if (i==0 || currentlayerStack != layerStack) {
1574 currentlayerStack = layerStack;
1575 // figure out if this layerstack is mirrored
1576 // (more than one display) if so, pick the default display,
1577 // if not, pick the only display it's on.
1578 disp.clear();
1579 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1580 sp<const DisplayDevice> hw(mDisplays[dpy]);
1581 if (hw->getLayerStack() == currentlayerStack) {
1582 if (disp == NULL) {
1583 disp = hw;
1584 } else {
1585 disp = NULL;
1586 break;
1587 }
1588 }
1589 }
1590 }
1591 if (disp == NULL) {
1592 // NOTE: TEMPORARY FIX ONLY. Real fix should cause layers to
1593 // redraw after transform hint changes. See bug 8508397.
1594
1595 // could be null when this layer is using a layerStack
1596 // that is not visible on any display. Also can occur at
1597 // screen off/on times.
1598 disp = getDefaultDisplayDevice();
1599 }
1600 layer->updateTransformHint(disp);
1601 }
1602 }
1603
1604
1605 /*
1606 * Perform our own transaction if needed
1607 */
1608
1609 const LayerVector& layers(mDrawingState.layersSortedByZ);
1610 if (currentLayers.size() > layers.size()) {
1611 // layers have been added
1612 mVisibleRegionsDirty = true;
1613 }
1614
1615 // some layers might have been removed, so
1616 // we need to update the regions they're exposing.
1617 if (mLayersRemoved) {
1618 mLayersRemoved = false;
1619 mVisibleRegionsDirty = true;
1620 const size_t count = layers.size();
1621 for (size_t i=0 ; i<count ; i++) {
1622 const sp<Layer>& layer(layers[i]);
1623 if (currentLayers.indexOf(layer) < 0) {
1624 // this layer is not visible anymore
1625 // TODO: we could traverse the tree from front to back and
1626 // compute the actual visible region
1627 // TODO: we could cache the transformed region
1628 const Layer::State& s(layer->getDrawingState());
Robert Carr3dcabfa2016-03-01 18:36:58 -08001629 Region visibleReg = s.active.transform.transform(
Dan Stoza9e56aa02015-11-02 13:00:03 -08001630 Region(Rect(s.active.w, s.active.h)));
1631 invalidateLayerStack(s.layerStack, visibleReg);
1632 }
1633 }
1634 }
1635
1636 commitTransaction();
1637
1638 updateCursorAsync();
1639}
1640
1641void SurfaceFlinger::updateCursorAsync()
1642{
1643 HWComposer& hwc(getHwComposer());
1644 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1645 sp<const DisplayDevice> hw(mDisplays[dpy]);
1646 const int32_t id = hw->getHwcDisplayId();
1647 if (id < 0) {
1648 continue;
1649 }
1650 const Vector< sp<Layer> >& currentLayers(
1651 hw->getVisibleLayersSortedByZ());
1652 const size_t count = currentLayers.size();
1653 HWComposer::LayerListIterator cur = hwc.begin(id);
1654 const HWComposer::LayerListIterator end = hwc.end(id);
1655 for (size_t i=0 ; cur!=end && i<count ; ++i, ++cur) {
1656 if (cur->getCompositionType() != HWC_CURSOR_OVERLAY) {
1657 continue;
1658 }
1659 const sp<Layer>& layer(currentLayers[i]);
1660 Rect cursorPos = layer->getPosition(hw);
1661 hwc.setCursorPositionAsync(id, cursorPos);
1662 break;
1663 }
1664 }
1665}
1666
1667void SurfaceFlinger::commitTransaction()
1668{
1669 if (!mLayersPendingRemoval.isEmpty()) {
1670 // Notify removed layers now that they can't be drawn from
1671 for (size_t i = 0; i < mLayersPendingRemoval.size(); i++) {
1672 mLayersPendingRemoval[i]->onRemoved();
1673 }
1674 mLayersPendingRemoval.clear();
1675 }
1676
1677 // If this transaction is part of a window animation then the next frame
1678 // we composite should be considered an animation as well.
1679 mAnimCompositionPending = mAnimTransactionPending;
1680
1681 mDrawingState = mCurrentState;
1682 mTransactionPending = false;
1683 mAnimTransactionPending = false;
1684 mTransactionCV.broadcast();
1685}
1686
1687void SurfaceFlinger::computeVisibleRegions(
1688 const LayerVector& currentLayers, uint32_t layerStack,
1689 Region& outDirtyRegion, Region& outOpaqueRegion)
1690{
1691 ATRACE_CALL();
1692
1693 Region aboveOpaqueLayers;
1694 Region aboveCoveredLayers;
1695 Region dirty;
1696
1697 outDirtyRegion.clear();
1698
1699 size_t i = currentLayers.size();
1700 while (i--) {
1701 const sp<Layer>& layer = currentLayers[i];
1702
1703 // start with the whole surface at its current location
1704 const Layer::State& s(layer->getDrawingState());
1705
1706 // only consider the layers on the given layer stack
1707 if (s.layerStack != layerStack)
1708 continue;
1709
1710 /*
1711 * opaqueRegion: area of a surface that is fully opaque.
1712 */
1713 Region opaqueRegion;
1714
1715 /*
1716 * visibleRegion: area of a surface that is visible on screen
1717 * and not fully transparent. This is essentially the layer's
1718 * footprint minus the opaque regions above it.
1719 * Areas covered by a translucent surface are considered visible.
1720 */
1721 Region visibleRegion;
1722
1723 /*
1724 * coveredRegion: area of a surface that is covered by all
1725 * visible regions above it (which includes the translucent areas).
1726 */
1727 Region coveredRegion;
1728
1729 /*
1730 * transparentRegion: area of a surface that is hinted to be completely
1731 * transparent. This is only used to tell when the layer has no visible
1732 * non-transparent regions and can be removed from the layer list. It
1733 * does not affect the visibleRegion of this layer or any layers
1734 * beneath it. The hint may not be correct if apps don't respect the
1735 * SurfaceView restrictions (which, sadly, some don't).
1736 */
1737 Region transparentRegion;
1738
1739
1740 // handle hidden surfaces by setting the visible region to empty
1741 if (CC_LIKELY(layer->isVisible())) {
1742 const bool translucent = !layer->isOpaque(s);
Robert Carr3dcabfa2016-03-01 18:36:58 -08001743 Rect bounds(s.active.transform.transform(layer->computeBounds()));
Dan Stoza9e56aa02015-11-02 13:00:03 -08001744 visibleRegion.set(bounds);
1745 if (!visibleRegion.isEmpty()) {
1746 // Remove the transparent area from the visible region
1747 if (translucent) {
Robert Carr3dcabfa2016-03-01 18:36:58 -08001748 const Transform tr(s.active.transform);
Dan Stoza9e56aa02015-11-02 13:00:03 -08001749 if (tr.transformed()) {
1750 if (tr.preserveRects()) {
1751 // transform the transparent region
1752 transparentRegion = tr.transform(s.activeTransparentRegion);
1753 } else {
1754 // transformation too complex, can't do the
1755 // transparent region optimization.
1756 transparentRegion.clear();
1757 }
1758 } else {
1759 transparentRegion = s.activeTransparentRegion;
1760 }
1761 }
1762
1763 // compute the opaque region
Robert Carr3dcabfa2016-03-01 18:36:58 -08001764 const int32_t layerOrientation = s.active.transform.getOrientation();
Dan Stoza9e56aa02015-11-02 13:00:03 -08001765 if (s.alpha==255 && !translucent &&
1766 ((layerOrientation & Transform::ROT_INVALID) == false)) {
1767 // the opaque region is the layer's footprint
1768 opaqueRegion = visibleRegion;
1769 }
1770 }
1771 }
1772
1773 // Clip the covered region to the visible region
1774 coveredRegion = aboveCoveredLayers.intersect(visibleRegion);
1775
1776 // Update aboveCoveredLayers for next (lower) layer
1777 aboveCoveredLayers.orSelf(visibleRegion);
1778
1779 // subtract the opaque region covered by the layers above us
1780 visibleRegion.subtractSelf(aboveOpaqueLayers);
1781
1782 // compute this layer's dirty region
1783 if (layer->contentDirty) {
1784 // we need to invalidate the whole region
1785 dirty = visibleRegion;
1786 // as well, as the old visible region
1787 dirty.orSelf(layer->visibleRegion);
1788 layer->contentDirty = false;
1789 } else {
1790 /* compute the exposed region:
1791 * the exposed region consists of two components:
1792 * 1) what's VISIBLE now and was COVERED before
1793 * 2) what's EXPOSED now less what was EXPOSED before
1794 *
1795 * note that (1) is conservative, we start with the whole
1796 * visible region but only keep what used to be covered by
1797 * something -- which mean it may have been exposed.
1798 *
1799 * (2) handles areas that were not covered by anything but got
1800 * exposed because of a resize.
1801 */
1802 const Region newExposed = visibleRegion - coveredRegion;
1803 const Region oldVisibleRegion = layer->visibleRegion;
1804 const Region oldCoveredRegion = layer->coveredRegion;
1805 const Region oldExposed = oldVisibleRegion - oldCoveredRegion;
1806 dirty = (visibleRegion&oldCoveredRegion) | (newExposed-oldExposed);
1807 }
1808 dirty.subtractSelf(aboveOpaqueLayers);
1809
1810 // accumulate to the screen dirty region
1811 outDirtyRegion.orSelf(dirty);
1812
1813 // Update aboveOpaqueLayers for next (lower) layer
1814 aboveOpaqueLayers.orSelf(opaqueRegion);
1815
1816 // Store the visible region in screen space
1817 layer->setVisibleRegion(visibleRegion);
1818 layer->setCoveredRegion(coveredRegion);
1819 layer->setVisibleNonTransparentRegion(
1820 visibleRegion.subtract(transparentRegion));
1821 }
1822
1823 outOpaqueRegion = aboveOpaqueLayers;
1824}
1825
1826void SurfaceFlinger::invalidateLayerStack(uint32_t layerStack,
1827 const Region& dirty) {
1828 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
1829 const sp<DisplayDevice>& hw(mDisplays[dpy]);
1830 if (hw->getLayerStack() == layerStack) {
1831 hw->dirtyRegion.orSelf(dirty);
1832 }
1833 }
1834}
1835
1836bool SurfaceFlinger::handlePageFlip()
1837{
1838 Region dirtyRegion;
1839
1840 bool visibleRegions = false;
1841 const LayerVector& layers(mDrawingState.layersSortedByZ);
1842 bool frameQueued = false;
1843
1844 // Store the set of layers that need updates. This set must not change as
1845 // buffers are being latched, as this could result in a deadlock.
1846 // Example: Two producers share the same command stream and:
1847 // 1.) Layer 0 is latched
1848 // 2.) Layer 0 gets a new frame
1849 // 2.) Layer 1 gets a new frame
1850 // 3.) Layer 1 is latched.
1851 // Display is now waiting on Layer 1's frame, which is behind layer 0's
1852 // second frame. But layer 0's second frame could be waiting on display.
1853 Vector<Layer*> layersWithQueuedFrames;
1854 for (size_t i = 0, count = layers.size(); i<count ; i++) {
1855 const sp<Layer>& layer(layers[i]);
1856 if (layer->hasQueuedFrame()) {
1857 frameQueued = true;
1858 if (layer->shouldPresentNow(mPrimaryDispSync)) {
1859 layersWithQueuedFrames.push_back(layer.get());
1860 } else {
1861 layer->useEmptyDamage();
1862 }
1863 } else {
1864 layer->useEmptyDamage();
1865 }
1866 }
1867 for (size_t i = 0, count = layersWithQueuedFrames.size() ; i<count ; i++) {
1868 Layer* layer = layersWithQueuedFrames[i];
1869 const Region dirty(layer->latchBuffer(visibleRegions));
1870 layer->useSurfaceDamage();
1871 const Layer::State& s(layer->getDrawingState());
1872 invalidateLayerStack(s.layerStack, dirty);
1873 }
1874
1875 mVisibleRegionsDirty |= visibleRegions;
1876
1877 // If we will need to wake up at some time in the future to deal with a
1878 // queued frame that shouldn't be displayed during this vsync period, wake
1879 // up during the next vsync period to check again.
1880 if (frameQueued && layersWithQueuedFrames.empty()) {
1881 signalLayerUpdate();
1882 }
1883
1884 // Only continue with the refresh if there is actually new work to do
1885 return !layersWithQueuedFrames.empty();
1886}
1887
1888void SurfaceFlinger::invalidateHwcGeometry()
1889{
1890 mHwWorkListDirty = true;
1891}
1892
1893
1894void SurfaceFlinger::doDisplayComposition(const sp<const DisplayDevice>& hw,
1895 const Region& inDirtyRegion)
1896{
1897 // We only need to actually compose the display if:
1898 // 1) It is being handled by hardware composer, which may need this to
1899 // keep its virtual display state machine in sync, or
1900 // 2) There is work to be done (the dirty region isn't empty)
1901 bool isHwcDisplay = hw->getHwcDisplayId() >= 0;
1902 if (!isHwcDisplay && inDirtyRegion.isEmpty()) {
1903 return;
1904 }
1905
1906 Region dirtyRegion(inDirtyRegion);
1907
1908 // compute the invalid region
1909 hw->swapRegion.orSelf(dirtyRegion);
1910
1911 uint32_t flags = hw->getFlags();
1912 if (flags & DisplayDevice::SWAP_RECTANGLE) {
1913 // we can redraw only what's dirty, but since SWAP_RECTANGLE only
1914 // takes a rectangle, we must make sure to update that whole
1915 // rectangle in that case
1916 dirtyRegion.set(hw->swapRegion.bounds());
1917 } else {
1918 if (flags & DisplayDevice::PARTIAL_UPDATES) {
1919 // We need to redraw the rectangle that will be updated
1920 // (pushed to the framebuffer).
1921 // This is needed because PARTIAL_UPDATES only takes one
1922 // rectangle instead of a region (see DisplayDevice::flip())
1923 dirtyRegion.set(hw->swapRegion.bounds());
1924 } else {
1925 // we need to redraw everything (the whole screen)
1926 dirtyRegion.set(hw->bounds());
1927 hw->swapRegion = dirtyRegion;
1928 }
1929 }
1930
1931 if (CC_LIKELY(!mDaltonize && !mHasColorMatrix)) {
1932 if (!doComposeSurfaces(hw, dirtyRegion)) return;
1933 } else {
1934 RenderEngine& engine(getRenderEngine());
1935 mat4 colorMatrix = mColorMatrix;
1936 if (mDaltonize) {
1937 colorMatrix = colorMatrix * mDaltonizer();
1938 }
1939 mat4 oldMatrix = engine.setupColorTransform(colorMatrix);
1940 doComposeSurfaces(hw, dirtyRegion);
1941 engine.setupColorTransform(oldMatrix);
1942 }
1943
1944 // update the swap region and clear the dirty region
1945 hw->swapRegion.orSelf(dirtyRegion);
1946
1947 // swap buffers (presentation)
1948 hw->swapBuffers(getHwComposer());
1949}
1950
1951bool SurfaceFlinger::doComposeSurfaces(const sp<const DisplayDevice>& hw, const Region& dirty)
1952{
1953 RenderEngine& engine(getRenderEngine());
1954 const int32_t id = hw->getHwcDisplayId();
1955 HWComposer& hwc(getHwComposer());
1956 HWComposer::LayerListIterator cur = hwc.begin(id);
1957 const HWComposer::LayerListIterator end = hwc.end(id);
1958
1959 bool hasGlesComposition = hwc.hasGlesComposition(id);
1960 if (hasGlesComposition) {
1961 if (!hw->makeCurrent(mEGLDisplay, mEGLContext)) {
1962 ALOGW("DisplayDevice::makeCurrent failed. Aborting surface composition for display %s",
1963 hw->getDisplayName().string());
1964 eglMakeCurrent(mEGLDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
1965 if(!getDefaultDisplayDevice()->makeCurrent(mEGLDisplay, mEGLContext)) {
1966 ALOGE("DisplayDevice::makeCurrent on default display failed. Aborting.");
1967 }
1968 return false;
1969 }
1970
1971 // Never touch the framebuffer if we don't have any framebuffer layers
1972 const bool hasHwcComposition = hwc.hasHwcComposition(id);
1973 if (hasHwcComposition) {
1974 // when using overlays, we assume a fully transparent framebuffer
1975 // NOTE: we could reduce how much we need to clear, for instance
1976 // remove where there are opaque FB layers. however, on some
1977 // GPUs doing a "clean slate" clear might be more efficient.
1978 // We'll revisit later if needed.
1979 engine.clearWithColor(0, 0, 0, 0);
1980 } else {
1981 // we start with the whole screen area
1982 const Region bounds(hw->getBounds());
1983
1984 // we remove the scissor part
1985 // we're left with the letterbox region
1986 // (common case is that letterbox ends-up being empty)
1987 const Region letterbox(bounds.subtract(hw->getScissor()));
1988
1989 // compute the area to clear
1990 Region region(hw->undefinedRegion.merge(letterbox));
1991
1992 // but limit it to the dirty region
1993 region.andSelf(dirty);
1994
1995 // screen is already cleared here
1996 if (!region.isEmpty()) {
1997 // can happen with SurfaceView
1998 drawWormhole(hw, region);
1999 }
2000 }
2001
2002 if (hw->getDisplayType() != DisplayDevice::DISPLAY_PRIMARY) {
2003 // just to be on the safe side, we don't set the
2004 // scissor on the main display. It should never be needed
2005 // anyways (though in theory it could since the API allows it).
2006 const Rect& bounds(hw->getBounds());
2007 const Rect& scissor(hw->getScissor());
2008 if (scissor != bounds) {
2009 // scissor doesn't match the screen's dimensions, so we
2010 // need to clear everything outside of it and enable
2011 // the GL scissor so we don't draw anything where we shouldn't
2012
2013 // enable scissor for this frame
2014 const uint32_t height = hw->getHeight();
2015 engine.setScissor(scissor.left, height - scissor.bottom,
2016 scissor.getWidth(), scissor.getHeight());
2017 }
2018 }
2019 }
2020
2021 /*
2022 * and then, render the layers targeted at the framebuffer
2023 */
2024
2025 const Vector< sp<Layer> >& layers(hw->getVisibleLayersSortedByZ());
2026 const size_t count = layers.size();
2027 const Transform& tr = hw->getTransform();
2028 if (cur != end) {
2029 // we're using h/w composer
2030 for (size_t i=0 ; i<count && cur!=end ; ++i, ++cur) {
2031 const sp<Layer>& layer(layers[i]);
2032 const Region clip(dirty.intersect(tr.transform(layer->visibleRegion)));
2033 if (!clip.isEmpty()) {
2034 switch (cur->getCompositionType()) {
2035 case HWC_CURSOR_OVERLAY:
2036 case HWC_OVERLAY: {
2037 const Layer::State& state(layer->getDrawingState());
2038 if ((cur->getHints() & HWC_HINT_CLEAR_FB)
2039 && i
2040 && layer->isOpaque(state) && (state.alpha == 0xFF)
2041 && hasGlesComposition) {
2042 // never clear the very first layer since we're
2043 // guaranteed the FB is already cleared
2044 layer->clearWithOpenGL(hw, clip);
2045 }
2046 break;
2047 }
2048 case HWC_FRAMEBUFFER: {
2049 layer->draw(hw, clip);
2050 break;
2051 }
2052 case HWC_FRAMEBUFFER_TARGET: {
2053 // this should not happen as the iterator shouldn't
2054 // let us get there.
2055 ALOGW("HWC_FRAMEBUFFER_TARGET found in hwc list (index=%zu)", i);
2056 break;
2057 }
2058 }
2059 }
2060 layer->setAcquireFence(hw, *cur);
2061 }
2062 } else {
2063 // we're not using h/w composer
2064 for (size_t i=0 ; i<count ; ++i) {
2065 const sp<Layer>& layer(layers[i]);
2066 const Region clip(dirty.intersect(
2067 tr.transform(layer->visibleRegion)));
2068 if (!clip.isEmpty()) {
2069 layer->draw(hw, clip);
2070 }
2071 }
2072 }
2073
2074 // disable scissor at the end of the frame
2075 engine.disableScissor();
2076 return true;
2077}
2078
2079void SurfaceFlinger::drawWormhole(const sp<const DisplayDevice>& hw, const Region& region) const {
2080 const int32_t height = hw->getHeight();
2081 RenderEngine& engine(getRenderEngine());
2082 engine.fillRegionWithColor(region, height, 0, 0, 0, 0);
2083}
2084
2085status_t SurfaceFlinger::addClientLayer(const sp<Client>& client,
2086 const sp<IBinder>& handle,
2087 const sp<IGraphicBufferProducer>& gbc,
2088 const sp<Layer>& lbc)
2089{
2090 // add this layer to the current state list
2091 {
2092 Mutex::Autolock _l(mStateLock);
2093 if (mCurrentState.layersSortedByZ.size() >= MAX_LAYERS) {
2094 return NO_MEMORY;
2095 }
2096 mCurrentState.layersSortedByZ.add(lbc);
2097 mGraphicBufferProducerList.add(IInterface::asBinder(gbc));
2098 }
2099
2100 // attach this layer to the client
2101 client->attachLayer(handle, lbc);
2102
2103 return NO_ERROR;
2104}
2105
2106status_t SurfaceFlinger::removeLayer(const sp<Layer>& layer) {
2107 Mutex::Autolock _l(mStateLock);
2108 ssize_t index = mCurrentState.layersSortedByZ.remove(layer);
2109 if (index >= 0) {
2110 mLayersPendingRemoval.push(layer);
2111 mLayersRemoved = true;
2112 setTransactionFlags(eTransactionNeeded);
2113 return NO_ERROR;
2114 }
2115 return status_t(index);
2116}
2117
2118uint32_t SurfaceFlinger::peekTransactionFlags(uint32_t /* flags */) {
2119 return android_atomic_release_load(&mTransactionFlags);
2120}
2121
2122uint32_t SurfaceFlinger::getTransactionFlags(uint32_t flags) {
2123 return android_atomic_and(~flags, &mTransactionFlags) & flags;
2124}
2125
2126uint32_t SurfaceFlinger::setTransactionFlags(uint32_t flags) {
2127 uint32_t old = android_atomic_or(flags, &mTransactionFlags);
2128 if ((old & flags)==0) { // wake the server up
2129 signalTransaction();
2130 }
2131 return old;
2132}
2133
2134void SurfaceFlinger::setTransactionState(
2135 const Vector<ComposerState>& state,
2136 const Vector<DisplayState>& displays,
2137 uint32_t flags)
2138{
2139 ATRACE_CALL();
2140 Mutex::Autolock _l(mStateLock);
2141 uint32_t transactionFlags = 0;
2142
2143 if (flags & eAnimation) {
2144 // For window updates that are part of an animation we must wait for
2145 // previous animation "frames" to be handled.
2146 while (mAnimTransactionPending) {
2147 status_t err = mTransactionCV.waitRelative(mStateLock, s2ns(5));
2148 if (CC_UNLIKELY(err != NO_ERROR)) {
2149 // just in case something goes wrong in SF, return to the
2150 // caller after a few seconds.
2151 ALOGW_IF(err == TIMED_OUT, "setTransactionState timed out "
2152 "waiting for previous animation frame");
2153 mAnimTransactionPending = false;
2154 break;
2155 }
2156 }
2157 }
2158
2159 size_t count = displays.size();
2160 for (size_t i=0 ; i<count ; i++) {
2161 const DisplayState& s(displays[i]);
2162 transactionFlags |= setDisplayStateLocked(s);
2163 }
2164
2165 count = state.size();
2166 for (size_t i=0 ; i<count ; i++) {
2167 const ComposerState& s(state[i]);
2168 // Here we need to check that the interface we're given is indeed
2169 // one of our own. A malicious client could give us a NULL
2170 // IInterface, or one of its own or even one of our own but a
2171 // different type. All these situations would cause us to crash.
2172 //
2173 // NOTE: it would be better to use RTTI as we could directly check
2174 // that we have a Client*. however, RTTI is disabled in Android.
2175 if (s.client != NULL) {
2176 sp<IBinder> binder = IInterface::asBinder(s.client);
2177 if (binder != NULL) {
2178 String16 desc(binder->getInterfaceDescriptor());
2179 if (desc == ISurfaceComposerClient::descriptor) {
2180 sp<Client> client( static_cast<Client *>(s.client.get()) );
2181 transactionFlags |= setClientStateLocked(client, s.state);
2182 }
2183 }
2184 }
2185 }
2186
2187 if (transactionFlags) {
2188 // this triggers the transaction
2189 setTransactionFlags(transactionFlags);
2190
2191 // if this is a synchronous transaction, wait for it to take effect
2192 // before returning.
2193 if (flags & eSynchronous) {
2194 mTransactionPending = true;
2195 }
2196 if (flags & eAnimation) {
2197 mAnimTransactionPending = true;
2198 }
2199 while (mTransactionPending) {
2200 status_t err = mTransactionCV.waitRelative(mStateLock, s2ns(5));
2201 if (CC_UNLIKELY(err != NO_ERROR)) {
2202 // just in case something goes wrong in SF, return to the
2203 // called after a few seconds.
2204 ALOGW_IF(err == TIMED_OUT, "setTransactionState timed out!");
2205 mTransactionPending = false;
2206 break;
2207 }
2208 }
2209 }
2210}
2211
2212uint32_t SurfaceFlinger::setDisplayStateLocked(const DisplayState& s)
2213{
2214 ssize_t dpyIdx = mCurrentState.displays.indexOfKey(s.token);
2215 if (dpyIdx < 0)
2216 return 0;
2217
2218 uint32_t flags = 0;
2219 DisplayDeviceState& disp(mCurrentState.displays.editValueAt(dpyIdx));
2220 if (disp.isValid()) {
2221 const uint32_t what = s.what;
2222 if (what & DisplayState::eSurfaceChanged) {
2223 if (IInterface::asBinder(disp.surface) != IInterface::asBinder(s.surface)) {
2224 disp.surface = s.surface;
2225 flags |= eDisplayTransactionNeeded;
2226 }
2227 }
2228 if (what & DisplayState::eLayerStackChanged) {
2229 if (disp.layerStack != s.layerStack) {
2230 disp.layerStack = s.layerStack;
2231 flags |= eDisplayTransactionNeeded;
2232 }
2233 }
2234 if (what & DisplayState::eDisplayProjectionChanged) {
2235 if (disp.orientation != s.orientation) {
2236 disp.orientation = s.orientation;
2237 flags |= eDisplayTransactionNeeded;
2238 }
2239 if (disp.frame != s.frame) {
2240 disp.frame = s.frame;
2241 flags |= eDisplayTransactionNeeded;
2242 }
2243 if (disp.viewport != s.viewport) {
2244 disp.viewport = s.viewport;
2245 flags |= eDisplayTransactionNeeded;
2246 }
2247 }
2248 if (what & DisplayState::eDisplaySizeChanged) {
2249 if (disp.width != s.width) {
2250 disp.width = s.width;
2251 flags |= eDisplayTransactionNeeded;
2252 }
2253 if (disp.height != s.height) {
2254 disp.height = s.height;
2255 flags |= eDisplayTransactionNeeded;
2256 }
2257 }
2258 }
2259 return flags;
2260}
2261
2262uint32_t SurfaceFlinger::setClientStateLocked(
2263 const sp<Client>& client,
2264 const layer_state_t& s)
2265{
2266 uint32_t flags = 0;
2267 sp<Layer> layer(client->getLayerUser(s.surface));
2268 if (layer != 0) {
2269 const uint32_t what = s.what;
2270 if (what & layer_state_t::ePositionChanged) {
2271 if (layer->setPosition(s.x, s.y))
2272 flags |= eTraversalNeeded;
2273 }
2274 if (what & layer_state_t::eLayerChanged) {
2275 // NOTE: index needs to be calculated before we update the state
2276 ssize_t idx = mCurrentState.layersSortedByZ.indexOf(layer);
2277 if (layer->setLayer(s.z) && idx >= 0) {
2278 mCurrentState.layersSortedByZ.removeAt(idx);
2279 mCurrentState.layersSortedByZ.add(layer);
2280 // we need traversal (state changed)
2281 // AND transaction (list changed)
2282 flags |= eTransactionNeeded|eTraversalNeeded;
2283 }
2284 }
2285 if (what & layer_state_t::eSizeChanged) {
2286 if (layer->setSize(s.w, s.h)) {
2287 flags |= eTraversalNeeded;
2288 }
2289 }
2290 if (what & layer_state_t::eAlphaChanged) {
2291 if (layer->setAlpha(uint8_t(255.0f*s.alpha+0.5f)))
2292 flags |= eTraversalNeeded;
2293 }
2294 if (what & layer_state_t::eMatrixChanged) {
2295 if (layer->setMatrix(s.matrix))
2296 flags |= eTraversalNeeded;
2297 }
2298 if (what & layer_state_t::eTransparentRegionChanged) {
2299 if (layer->setTransparentRegionHint(s.transparentRegion))
2300 flags |= eTraversalNeeded;
2301 }
2302 if (what & layer_state_t::eFlagsChanged) {
2303 if (layer->setFlags(s.flags, s.mask))
2304 flags |= eTraversalNeeded;
2305 }
2306 if (what & layer_state_t::eCropChanged) {
2307 if (layer->setCrop(s.crop))
2308 flags |= eTraversalNeeded;
2309 }
Pablo Ceballosacbe6782016-03-04 17:54:21 +00002310 if (what & layer_state_t::eFinalCropChanged) {
2311 if (layer->setFinalCrop(s.finalCrop))
2312 flags |= eTraversalNeeded;
2313 }
Dan Stoza9e56aa02015-11-02 13:00:03 -08002314 if (what & layer_state_t::eLayerStackChanged) {
2315 // NOTE: index needs to be calculated before we update the state
2316 ssize_t idx = mCurrentState.layersSortedByZ.indexOf(layer);
2317 if (layer->setLayerStack(s.layerStack) && idx >= 0) {
2318 mCurrentState.layersSortedByZ.removeAt(idx);
2319 mCurrentState.layersSortedByZ.add(layer);
2320 // we need traversal (state changed)
2321 // AND transaction (list changed)
2322 flags |= eTransactionNeeded|eTraversalNeeded;
2323 }
2324 }
2325 if (what & layer_state_t::eDeferTransaction) {
2326 layer->deferTransactionUntil(s.handle, s.frameNumber);
2327 // We don't trigger a traversal here because if no other state is
2328 // changed, we don't want this to cause any more work
2329 }
2330 }
2331 return flags;
2332}
2333
2334status_t SurfaceFlinger::createLayer(
2335 const String8& name,
2336 const sp<Client>& client,
2337 uint32_t w, uint32_t h, PixelFormat format, uint32_t flags,
2338 sp<IBinder>* handle, sp<IGraphicBufferProducer>* gbp)
2339{
2340 //ALOGD("createLayer for (%d x %d), name=%s", w, h, name.string());
2341 if (int32_t(w|h) < 0) {
2342 ALOGE("createLayer() failed, w or h is negative (w=%d, h=%d)",
2343 int(w), int(h));
2344 return BAD_VALUE;
2345 }
2346
2347 status_t result = NO_ERROR;
2348
2349 sp<Layer> layer;
2350
2351 switch (flags & ISurfaceComposerClient::eFXSurfaceMask) {
2352 case ISurfaceComposerClient::eFXSurfaceNormal:
2353 result = createNormalLayer(client,
2354 name, w, h, flags, format,
2355 handle, gbp, &layer);
2356 break;
2357 case ISurfaceComposerClient::eFXSurfaceDim:
2358 result = createDimLayer(client,
2359 name, w, h, flags,
2360 handle, gbp, &layer);
2361 break;
2362 default:
2363 result = BAD_VALUE;
2364 break;
2365 }
2366
2367 if (result != NO_ERROR) {
2368 return result;
2369 }
2370
2371 result = addClientLayer(client, *handle, *gbp, layer);
2372 if (result != NO_ERROR) {
2373 return result;
2374 }
2375
2376 setTransactionFlags(eTransactionNeeded);
2377 return result;
2378}
2379
2380status_t SurfaceFlinger::createNormalLayer(const sp<Client>& client,
2381 const String8& name, uint32_t w, uint32_t h, uint32_t flags, PixelFormat& format,
2382 sp<IBinder>* handle, sp<IGraphicBufferProducer>* gbp, sp<Layer>* outLayer)
2383{
2384 // initialize the surfaces
2385 switch (format) {
2386 case PIXEL_FORMAT_TRANSPARENT:
2387 case PIXEL_FORMAT_TRANSLUCENT:
2388 format = PIXEL_FORMAT_RGBA_8888;
2389 break;
2390 case PIXEL_FORMAT_OPAQUE:
2391 format = PIXEL_FORMAT_RGBX_8888;
2392 break;
2393 }
2394
2395 *outLayer = new Layer(this, client, name, w, h, flags);
2396 status_t err = (*outLayer)->setBuffers(w, h, format, flags);
2397 if (err == NO_ERROR) {
2398 *handle = (*outLayer)->getHandle();
2399 *gbp = (*outLayer)->getProducer();
2400 }
2401
2402 ALOGE_IF(err, "createNormalLayer() failed (%s)", strerror(-err));
2403 return err;
2404}
2405
2406status_t SurfaceFlinger::createDimLayer(const sp<Client>& client,
2407 const String8& name, uint32_t w, uint32_t h, uint32_t flags,
2408 sp<IBinder>* handle, sp<IGraphicBufferProducer>* gbp, sp<Layer>* outLayer)
2409{
2410 *outLayer = new LayerDim(this, client, name, w, h, flags);
2411 *handle = (*outLayer)->getHandle();
2412 *gbp = (*outLayer)->getProducer();
2413 return NO_ERROR;
2414}
2415
2416status_t SurfaceFlinger::onLayerRemoved(const sp<Client>& client, const sp<IBinder>& handle)
2417{
2418 // called by the window manager when it wants to remove a Layer
2419 status_t err = NO_ERROR;
2420 sp<Layer> l(client->getLayerUser(handle));
2421 if (l != NULL) {
2422 err = removeLayer(l);
2423 ALOGE_IF(err<0 && err != NAME_NOT_FOUND,
2424 "error removing layer=%p (%s)", l.get(), strerror(-err));
2425 }
2426 return err;
2427}
2428
2429status_t SurfaceFlinger::onLayerDestroyed(const wp<Layer>& layer)
2430{
2431 // called by ~LayerCleaner() when all references to the IBinder (handle)
2432 // are gone
2433 status_t err = NO_ERROR;
2434 sp<Layer> l(layer.promote());
2435 if (l != NULL) {
2436 err = removeLayer(l);
2437 ALOGE_IF(err<0 && err != NAME_NOT_FOUND,
2438 "error removing layer=%p (%s)", l.get(), strerror(-err));
2439 }
2440 return err;
2441}
2442
2443// ---------------------------------------------------------------------------
2444
2445void SurfaceFlinger::onInitializeDisplays() {
2446 // reset screen orientation and use primary layer stack
2447 Vector<ComposerState> state;
2448 Vector<DisplayState> displays;
2449 DisplayState d;
2450 d.what = DisplayState::eDisplayProjectionChanged |
2451 DisplayState::eLayerStackChanged;
2452 d.token = mBuiltinDisplays[DisplayDevice::DISPLAY_PRIMARY];
2453 d.layerStack = 0;
2454 d.orientation = DisplayState::eOrientationDefault;
2455 d.frame.makeInvalid();
2456 d.viewport.makeInvalid();
2457 d.width = 0;
2458 d.height = 0;
2459 displays.add(d);
2460 setTransactionState(state, displays, 0);
2461 setPowerModeInternal(getDisplayDevice(d.token), HWC_POWER_MODE_NORMAL);
2462
2463 const nsecs_t period =
2464 getHwComposer().getRefreshPeriod(HWC_DISPLAY_PRIMARY);
2465 mAnimFrameTracker.setDisplayRefreshPeriod(period);
2466}
2467
2468void SurfaceFlinger::initializeDisplays() {
2469 class MessageScreenInitialized : public MessageBase {
2470 SurfaceFlinger* flinger;
2471 public:
2472 MessageScreenInitialized(SurfaceFlinger* flinger) : flinger(flinger) { }
2473 virtual bool handler() {
2474 flinger->onInitializeDisplays();
2475 return true;
2476 }
2477 };
2478 sp<MessageBase> msg = new MessageScreenInitialized(this);
2479 postMessageAsync(msg); // we may be called from main thread, use async message
2480}
2481
2482void SurfaceFlinger::setPowerModeInternal(const sp<DisplayDevice>& hw,
2483 int mode) {
2484 ALOGD("Set power mode=%d, type=%d flinger=%p", mode, hw->getDisplayType(),
2485 this);
2486 int32_t type = hw->getDisplayType();
2487 int currentMode = hw->getPowerMode();
2488
2489 if (mode == currentMode) {
2490 ALOGD("Screen type=%d is already mode=%d", hw->getDisplayType(), mode);
2491 return;
2492 }
2493
2494 hw->setPowerMode(mode);
2495 if (type >= DisplayDevice::NUM_BUILTIN_DISPLAY_TYPES) {
2496 ALOGW("Trying to set power mode for virtual display");
2497 return;
2498 }
2499
2500 if (currentMode == HWC_POWER_MODE_OFF) {
2501 getHwComposer().setPowerMode(type, mode);
2502 if (type == DisplayDevice::DISPLAY_PRIMARY) {
2503 // FIXME: eventthread only knows about the main display right now
2504 mEventThread->onScreenAcquired();
2505 resyncToHardwareVsync(true);
2506 }
2507
2508 mVisibleRegionsDirty = true;
2509 mHasPoweredOff = true;
2510 repaintEverything();
2511 } else if (mode == HWC_POWER_MODE_OFF) {
2512 if (type == DisplayDevice::DISPLAY_PRIMARY) {
2513 disableHardwareVsync(true); // also cancels any in-progress resync
2514
2515 // FIXME: eventthread only knows about the main display right now
2516 mEventThread->onScreenReleased();
2517 }
2518
2519 getHwComposer().setPowerMode(type, mode);
2520 mVisibleRegionsDirty = true;
2521 // from this point on, SF will stop drawing on this display
2522 } else {
2523 getHwComposer().setPowerMode(type, mode);
2524 }
2525}
2526
2527void SurfaceFlinger::setPowerMode(const sp<IBinder>& display, int mode) {
2528 class MessageSetPowerMode: public MessageBase {
2529 SurfaceFlinger& mFlinger;
2530 sp<IBinder> mDisplay;
2531 int mMode;
2532 public:
2533 MessageSetPowerMode(SurfaceFlinger& flinger,
2534 const sp<IBinder>& disp, int mode) : mFlinger(flinger),
2535 mDisplay(disp) { mMode = mode; }
2536 virtual bool handler() {
2537 sp<DisplayDevice> hw(mFlinger.getDisplayDevice(mDisplay));
2538 if (hw == NULL) {
2539 ALOGE("Attempt to set power mode = %d for null display %p",
2540 mMode, mDisplay.get());
2541 } else if (hw->getDisplayType() >= DisplayDevice::DISPLAY_VIRTUAL) {
2542 ALOGW("Attempt to set power mode = %d for virtual display",
2543 mMode);
2544 } else {
2545 mFlinger.setPowerModeInternal(hw, mMode);
2546 }
2547 return true;
2548 }
2549 };
2550 sp<MessageBase> msg = new MessageSetPowerMode(*this, display, mode);
2551 postMessageSync(msg);
2552}
2553
2554// ---------------------------------------------------------------------------
2555
2556status_t SurfaceFlinger::dump(int fd, const Vector<String16>& args)
2557{
2558 String8 result;
2559
2560 IPCThreadState* ipc = IPCThreadState::self();
2561 const int pid = ipc->getCallingPid();
2562 const int uid = ipc->getCallingUid();
2563 if ((uid != AID_SHELL) &&
2564 !PermissionCache::checkPermission(sDump, pid, uid)) {
2565 result.appendFormat("Permission Denial: "
2566 "can't dump SurfaceFlinger from pid=%d, uid=%d\n", pid, uid);
2567 } else {
2568 // Try to get the main lock, but give up after one second
2569 // (this would indicate SF is stuck, but we want to be able to
2570 // print something in dumpsys).
2571 status_t err = mStateLock.timedLock(s2ns(1));
2572 bool locked = (err == NO_ERROR);
2573 if (!locked) {
2574 result.appendFormat(
2575 "SurfaceFlinger appears to be unresponsive (%s [%d]), "
2576 "dumping anyways (no locks held)\n", strerror(-err), err);
2577 }
2578
2579 bool dumpAll = true;
2580 size_t index = 0;
2581 size_t numArgs = args.size();
2582 if (numArgs) {
2583 if ((index < numArgs) &&
2584 (args[index] == String16("--list"))) {
2585 index++;
2586 listLayersLocked(args, index, result);
2587 dumpAll = false;
2588 }
2589
2590 if ((index < numArgs) &&
2591 (args[index] == String16("--latency"))) {
2592 index++;
2593 dumpStatsLocked(args, index, result);
2594 dumpAll = false;
2595 }
2596
2597 if ((index < numArgs) &&
2598 (args[index] == String16("--latency-clear"))) {
2599 index++;
2600 clearStatsLocked(args, index, result);
2601 dumpAll = false;
2602 }
2603
2604 if ((index < numArgs) &&
2605 (args[index] == String16("--dispsync"))) {
2606 index++;
2607 mPrimaryDispSync.dump(result);
2608 dumpAll = false;
2609 }
2610
2611 if ((index < numArgs) &&
2612 (args[index] == String16("--static-screen"))) {
2613 index++;
2614 dumpStaticScreenStats(result);
2615 dumpAll = false;
2616 }
Pablo Ceballos40845df2016-01-25 17:41:15 -08002617
Pablo Ceballos69a1a382016-03-30 15:28:05 -07002618#ifdef ENABLE_FENCE_TRACKING
Pablo Ceballos40845df2016-01-25 17:41:15 -08002619 if ((index < numArgs) &&
2620 (args[index] == String16("--fences"))) {
2621 index++;
2622 mFenceTracker.dump(&result);
2623 dumpAll = false;
2624 }
Pablo Ceballos69a1a382016-03-30 15:28:05 -07002625#endif
Dan Stoza9e56aa02015-11-02 13:00:03 -08002626 }
2627
2628 if (dumpAll) {
2629 dumpAllLocked(args, index, result);
2630 }
2631
2632 if (locked) {
2633 mStateLock.unlock();
2634 }
2635 }
2636 write(fd, result.string(), result.size());
2637 return NO_ERROR;
2638}
2639
2640void SurfaceFlinger::listLayersLocked(const Vector<String16>& /* args */,
2641 size_t& /* index */, String8& result) const
2642{
2643 const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2644 const size_t count = currentLayers.size();
2645 for (size_t i=0 ; i<count ; i++) {
2646 const sp<Layer>& layer(currentLayers[i]);
2647 result.appendFormat("%s\n", layer->getName().string());
2648 }
2649}
2650
2651void SurfaceFlinger::dumpStatsLocked(const Vector<String16>& args, size_t& index,
2652 String8& result) const
2653{
2654 String8 name;
2655 if (index < args.size()) {
2656 name = String8(args[index]);
2657 index++;
2658 }
2659
2660 const nsecs_t period =
2661 getHwComposer().getRefreshPeriod(HWC_DISPLAY_PRIMARY);
2662 result.appendFormat("%" PRId64 "\n", period);
2663
2664 if (name.isEmpty()) {
2665 mAnimFrameTracker.dumpStats(result);
2666 } else {
2667 const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2668 const size_t count = currentLayers.size();
2669 for (size_t i=0 ; i<count ; i++) {
2670 const sp<Layer>& layer(currentLayers[i]);
2671 if (name == layer->getName()) {
2672 layer->dumpFrameStats(result);
2673 }
2674 }
2675 }
2676}
2677
2678void SurfaceFlinger::clearStatsLocked(const Vector<String16>& args, size_t& index,
2679 String8& /* result */)
2680{
2681 String8 name;
2682 if (index < args.size()) {
2683 name = String8(args[index]);
2684 index++;
2685 }
2686
2687 const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2688 const size_t count = currentLayers.size();
2689 for (size_t i=0 ; i<count ; i++) {
2690 const sp<Layer>& layer(currentLayers[i]);
2691 if (name.isEmpty() || (name == layer->getName())) {
2692 layer->clearFrameStats();
2693 }
2694 }
2695
2696 mAnimFrameTracker.clearStats();
2697}
2698
2699// This should only be called from the main thread. Otherwise it would need
2700// the lock and should use mCurrentState rather than mDrawingState.
2701void SurfaceFlinger::logFrameStats() {
2702 const LayerVector& drawingLayers = mDrawingState.layersSortedByZ;
2703 const size_t count = drawingLayers.size();
2704 for (size_t i=0 ; i<count ; i++) {
2705 const sp<Layer>& layer(drawingLayers[i]);
2706 layer->logFrameStats();
2707 }
2708
2709 mAnimFrameTracker.logAndResetStats(String8("<win-anim>"));
2710}
2711
2712/*static*/ void SurfaceFlinger::appendSfConfigString(String8& result)
2713{
2714 static const char* config =
2715 " [sf"
2716#ifdef HAS_CONTEXT_PRIORITY
2717 " HAS_CONTEXT_PRIORITY"
2718#endif
2719#ifdef NEVER_DEFAULT_TO_ASYNC_MODE
2720 " NEVER_DEFAULT_TO_ASYNC_MODE"
2721#endif
2722#ifdef TARGET_DISABLE_TRIPLE_BUFFERING
2723 " TARGET_DISABLE_TRIPLE_BUFFERING"
2724#endif
2725 "]";
2726 result.append(config);
2727}
2728
2729void SurfaceFlinger::dumpStaticScreenStats(String8& result) const
2730{
2731 result.appendFormat("Static screen stats:\n");
2732 for (size_t b = 0; b < NUM_BUCKETS - 1; ++b) {
2733 float bucketTimeSec = mFrameBuckets[b] / 1e9;
2734 float percent = 100.0f *
2735 static_cast<float>(mFrameBuckets[b]) / mTotalTime;
2736 result.appendFormat(" < %zd frames: %.3f s (%.1f%%)\n",
2737 b + 1, bucketTimeSec, percent);
2738 }
2739 float bucketTimeSec = mFrameBuckets[NUM_BUCKETS - 1] / 1e9;
2740 float percent = 100.0f *
2741 static_cast<float>(mFrameBuckets[NUM_BUCKETS - 1]) / mTotalTime;
2742 result.appendFormat(" %zd+ frames: %.3f s (%.1f%%)\n",
2743 NUM_BUCKETS - 1, bucketTimeSec, percent);
2744}
2745
2746void SurfaceFlinger::dumpAllLocked(const Vector<String16>& args, size_t& index,
2747 String8& result) const
2748{
2749 bool colorize = false;
2750 if (index < args.size()
2751 && (args[index] == String16("--color"))) {
2752 colorize = true;
2753 index++;
2754 }
2755
2756 Colorizer colorizer(colorize);
2757
2758 // figure out if we're stuck somewhere
2759 const nsecs_t now = systemTime();
2760 const nsecs_t inSwapBuffers(mDebugInSwapBuffers);
2761 const nsecs_t inTransaction(mDebugInTransaction);
2762 nsecs_t inSwapBuffersDuration = (inSwapBuffers) ? now-inSwapBuffers : 0;
2763 nsecs_t inTransactionDuration = (inTransaction) ? now-inTransaction : 0;
2764
2765 /*
2766 * Dump library configuration.
2767 */
2768
2769 colorizer.bold(result);
2770 result.append("Build configuration:");
2771 colorizer.reset(result);
2772 appendSfConfigString(result);
2773 appendUiConfigString(result);
2774 appendGuiConfigString(result);
2775 result.append("\n");
2776
2777 colorizer.bold(result);
2778 result.append("Sync configuration: ");
2779 colorizer.reset(result);
2780 result.append(SyncFeatures::getInstance().toString());
2781 result.append("\n");
2782
2783 colorizer.bold(result);
2784 result.append("DispSync configuration: ");
2785 colorizer.reset(result);
2786 result.appendFormat("app phase %" PRId64 " ns, sf phase %" PRId64 " ns, "
2787 "present offset %d ns (refresh %" PRId64 " ns)",
2788 vsyncPhaseOffsetNs, sfVsyncPhaseOffsetNs, PRESENT_TIME_OFFSET_FROM_VSYNC_NS,
2789 mHwc->getRefreshPeriod(HWC_DISPLAY_PRIMARY));
2790 result.append("\n");
2791
2792 // Dump static screen stats
2793 result.append("\n");
2794 dumpStaticScreenStats(result);
2795 result.append("\n");
2796
2797 /*
2798 * Dump the visible layer list
2799 */
2800 const LayerVector& currentLayers = mCurrentState.layersSortedByZ;
2801 const size_t count = currentLayers.size();
2802 colorizer.bold(result);
2803 result.appendFormat("Visible layers (count = %zu)\n", count);
2804 colorizer.reset(result);
2805 for (size_t i=0 ; i<count ; i++) {
2806 const sp<Layer>& layer(currentLayers[i]);
2807 layer->dump(result, colorizer);
2808 }
2809
2810 /*
2811 * Dump Display state
2812 */
2813
2814 colorizer.bold(result);
2815 result.appendFormat("Displays (%zu entries)\n", mDisplays.size());
2816 colorizer.reset(result);
2817 for (size_t dpy=0 ; dpy<mDisplays.size() ; dpy++) {
2818 const sp<const DisplayDevice>& hw(mDisplays[dpy]);
2819 hw->dump(result);
2820 }
2821
2822 /*
2823 * Dump SurfaceFlinger global state
2824 */
2825
2826 colorizer.bold(result);
2827 result.append("SurfaceFlinger global state:\n");
2828 colorizer.reset(result);
2829
2830 HWComposer& hwc(getHwComposer());
2831 sp<const DisplayDevice> hw(getDefaultDisplayDevice());
2832
2833 colorizer.bold(result);
2834 result.appendFormat("EGL implementation : %s\n",
2835 eglQueryStringImplementationANDROID(mEGLDisplay, EGL_VERSION));
2836 colorizer.reset(result);
2837 result.appendFormat("%s\n",
2838 eglQueryStringImplementationANDROID(mEGLDisplay, EGL_EXTENSIONS));
2839
2840 mRenderEngine->dump(result);
2841
2842 hw->undefinedRegion.dump(result, "undefinedRegion");
2843 result.appendFormat(" orientation=%d, isDisplayOn=%d\n",
2844 hw->getOrientation(), hw->isDisplayOn());
2845 result.appendFormat(
2846 " last eglSwapBuffers() time: %f us\n"
2847 " last transaction time : %f us\n"
2848 " transaction-flags : %08x\n"
2849 " refresh-rate : %f fps\n"
2850 " x-dpi : %f\n"
2851 " y-dpi : %f\n"
2852 " gpu_to_cpu_unsupported : %d\n"
2853 ,
2854 mLastSwapBufferTime/1000.0,
2855 mLastTransactionTime/1000.0,
2856 mTransactionFlags,
2857 1e9 / hwc.getRefreshPeriod(HWC_DISPLAY_PRIMARY),
2858 hwc.getDpiX(HWC_DISPLAY_PRIMARY),
2859 hwc.getDpiY(HWC_DISPLAY_PRIMARY),
2860 !mGpuToCpuSupported);
2861
2862 result.appendFormat(" eglSwapBuffers time: %f us\n",
2863 inSwapBuffersDuration/1000.0);
2864
2865 result.appendFormat(" transaction time: %f us\n",
2866 inTransactionDuration/1000.0);
2867
2868 /*
2869 * VSYNC state
2870 */
2871 mEventThread->dump(result);
2872
2873 /*
2874 * Dump HWComposer state
2875 */
2876 colorizer.bold(result);
2877 result.append("h/w composer state:\n");
2878 colorizer.reset(result);
2879 result.appendFormat(" h/w composer %s and %s\n",
2880 hwc.initCheck()==NO_ERROR ? "present" : "not present",
2881 (mDebugDisableHWC || mDebugRegion || mDaltonize
2882 || mHasColorMatrix) ? "disabled" : "enabled");
2883 hwc.dump(result);
2884
2885 /*
2886 * Dump gralloc state
2887 */
2888 const GraphicBufferAllocator& alloc(GraphicBufferAllocator::get());
2889 alloc.dump(result);
2890}
2891
2892const Vector< sp<Layer> >&
2893SurfaceFlinger::getLayerSortedByZForHwcDisplay(int id) {
2894 // Note: mStateLock is held here
2895 wp<IBinder> dpy;
2896 for (size_t i=0 ; i<mDisplays.size() ; i++) {
2897 if (mDisplays.valueAt(i)->getHwcDisplayId() == id) {
2898 dpy = mDisplays.keyAt(i);
2899 break;
2900 }
2901 }
2902 if (dpy == NULL) {
2903 ALOGE("getLayerSortedByZForHwcDisplay: invalid hwc display id %d", id);
2904 // Just use the primary display so we have something to return
2905 dpy = getBuiltInDisplay(DisplayDevice::DISPLAY_PRIMARY);
2906 }
2907 return getDisplayDevice(dpy)->getVisibleLayersSortedByZ();
2908}
2909
2910bool SurfaceFlinger::startDdmConnection()
2911{
2912 void* libddmconnection_dso =
2913 dlopen("libsurfaceflinger_ddmconnection.so", RTLD_NOW);
2914 if (!libddmconnection_dso) {
2915 return false;
2916 }
2917 void (*DdmConnection_start)(const char* name);
2918 DdmConnection_start =
2919 (decltype(DdmConnection_start))dlsym(libddmconnection_dso, "DdmConnection_start");
2920 if (!DdmConnection_start) {
2921 dlclose(libddmconnection_dso);
2922 return false;
2923 }
2924 (*DdmConnection_start)(getServiceName());
2925 return true;
2926}
2927
2928status_t SurfaceFlinger::onTransact(
2929 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
2930{
2931 switch (code) {
2932 case CREATE_CONNECTION:
2933 case CREATE_DISPLAY:
2934 case SET_TRANSACTION_STATE:
2935 case BOOT_FINISHED:
2936 case CLEAR_ANIMATION_FRAME_STATS:
2937 case GET_ANIMATION_FRAME_STATS:
2938 case SET_POWER_MODE:
Dan Stozac4f471e2016-03-24 09:31:08 -07002939 case GET_HDR_CAPABILITIES:
Dan Stoza9e56aa02015-11-02 13:00:03 -08002940 {
2941 // codes that require permission check
2942 IPCThreadState* ipc = IPCThreadState::self();
2943 const int pid = ipc->getCallingPid();
2944 const int uid = ipc->getCallingUid();
2945 if ((uid != AID_GRAPHICS && uid != AID_SYSTEM) &&
2946 !PermissionCache::checkPermission(sAccessSurfaceFlinger, pid, uid)) {
2947 ALOGE("Permission Denial: "
2948 "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid);
2949 return PERMISSION_DENIED;
2950 }
2951 break;
2952 }
2953 case CAPTURE_SCREEN:
2954 {
2955 // codes that require permission check
2956 IPCThreadState* ipc = IPCThreadState::self();
2957 const int pid = ipc->getCallingPid();
2958 const int uid = ipc->getCallingUid();
2959 if ((uid != AID_GRAPHICS) &&
2960 !PermissionCache::checkPermission(sReadFramebuffer, pid, uid)) {
2961 ALOGE("Permission Denial: "
2962 "can't read framebuffer pid=%d, uid=%d", pid, uid);
2963 return PERMISSION_DENIED;
2964 }
2965 break;
2966 }
2967 }
2968
2969 status_t err = BnSurfaceComposer::onTransact(code, data, reply, flags);
2970 if (err == UNKNOWN_TRANSACTION || err == PERMISSION_DENIED) {
2971 CHECK_INTERFACE(ISurfaceComposer, data, reply);
2972 if (CC_UNLIKELY(!PermissionCache::checkCallingPermission(sHardwareTest))) {
2973 IPCThreadState* ipc = IPCThreadState::self();
2974 const int pid = ipc->getCallingPid();
2975 const int uid = ipc->getCallingUid();
2976 ALOGE("Permission Denial: "
2977 "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid);
2978 return PERMISSION_DENIED;
2979 }
2980 int n;
2981 switch (code) {
2982 case 1000: // SHOW_CPU, NOT SUPPORTED ANYMORE
2983 case 1001: // SHOW_FPS, NOT SUPPORTED ANYMORE
2984 return NO_ERROR;
2985 case 1002: // SHOW_UPDATES
2986 n = data.readInt32();
2987 mDebugRegion = n ? n : (mDebugRegion ? 0 : 1);
2988 invalidateHwcGeometry();
2989 repaintEverything();
2990 return NO_ERROR;
2991 case 1004:{ // repaint everything
2992 repaintEverything();
2993 return NO_ERROR;
2994 }
2995 case 1005:{ // force transaction
2996 setTransactionFlags(
2997 eTransactionNeeded|
2998 eDisplayTransactionNeeded|
2999 eTraversalNeeded);
3000 return NO_ERROR;
3001 }
3002 case 1006:{ // send empty update
3003 signalRefresh();
3004 return NO_ERROR;
3005 }
3006 case 1008: // toggle use of hw composer
3007 n = data.readInt32();
3008 mDebugDisableHWC = n ? 1 : 0;
3009 invalidateHwcGeometry();
3010 repaintEverything();
3011 return NO_ERROR;
3012 case 1009: // toggle use of transform hint
3013 n = data.readInt32();
3014 mDebugDisableTransformHint = n ? 1 : 0;
3015 invalidateHwcGeometry();
3016 repaintEverything();
3017 return NO_ERROR;
3018 case 1010: // interrogate.
3019 reply->writeInt32(0);
3020 reply->writeInt32(0);
3021 reply->writeInt32(mDebugRegion);
3022 reply->writeInt32(0);
3023 reply->writeInt32(mDebugDisableHWC);
3024 return NO_ERROR;
3025 case 1013: {
3026 Mutex::Autolock _l(mStateLock);
3027 sp<const DisplayDevice> hw(getDefaultDisplayDevice());
3028 reply->writeInt32(hw->getPageFlipCount());
3029 return NO_ERROR;
3030 }
3031 case 1014: {
3032 // daltonize
3033 n = data.readInt32();
3034 switch (n % 10) {
3035 case 1: mDaltonizer.setType(Daltonizer::protanomaly); break;
3036 case 2: mDaltonizer.setType(Daltonizer::deuteranomaly); break;
3037 case 3: mDaltonizer.setType(Daltonizer::tritanomaly); break;
3038 }
3039 if (n >= 10) {
3040 mDaltonizer.setMode(Daltonizer::correction);
3041 } else {
3042 mDaltonizer.setMode(Daltonizer::simulation);
3043 }
3044 mDaltonize = n > 0;
3045 invalidateHwcGeometry();
3046 repaintEverything();
3047 return NO_ERROR;
3048 }
3049 case 1015: {
3050 // apply a color matrix
3051 n = data.readInt32();
3052 mHasColorMatrix = n ? 1 : 0;
3053 if (n) {
3054 // color matrix is sent as mat3 matrix followed by vec3
3055 // offset, then packed into a mat4 where the last row is
3056 // the offset and extra values are 0
3057 for (size_t i = 0 ; i < 4; i++) {
3058 for (size_t j = 0; j < 4; j++) {
3059 mColorMatrix[i][j] = data.readFloat();
3060 }
3061 }
3062 } else {
3063 mColorMatrix = mat4();
3064 }
3065 invalidateHwcGeometry();
3066 repaintEverything();
3067 return NO_ERROR;
3068 }
3069 // This is an experimental interface
3070 // Needs to be shifted to proper binder interface when we productize
3071 case 1016: {
3072 n = data.readInt32();
3073 mPrimaryDispSync.setRefreshSkipCount(n);
3074 return NO_ERROR;
3075 }
3076 case 1017: {
3077 n = data.readInt32();
3078 mForceFullDamage = static_cast<bool>(n);
3079 return NO_ERROR;
3080 }
3081 case 1018: { // Modify Choreographer's phase offset
3082 n = data.readInt32();
3083 mEventThread->setPhaseOffset(static_cast<nsecs_t>(n));
3084 return NO_ERROR;
3085 }
3086 case 1019: { // Modify SurfaceFlinger's phase offset
3087 n = data.readInt32();
3088 mSFEventThread->setPhaseOffset(static_cast<nsecs_t>(n));
3089 return NO_ERROR;
3090 }
3091 }
3092 }
3093 return err;
3094}
3095
3096void SurfaceFlinger::repaintEverything() {
3097 android_atomic_or(1, &mRepaintEverything);
3098 signalTransaction();
3099}
3100
3101// ---------------------------------------------------------------------------
3102// Capture screen into an IGraphiBufferProducer
3103// ---------------------------------------------------------------------------
3104
3105/* The code below is here to handle b/8734824
3106 *
3107 * We create a IGraphicBufferProducer wrapper that forwards all calls
3108 * from the surfaceflinger thread to the calling binder thread, where they
3109 * are executed. This allows the calling thread in the calling process to be
3110 * reused and not depend on having "enough" binder threads to handle the
3111 * requests.
3112 */
3113class GraphicProducerWrapper : public BBinder, public MessageHandler {
3114 /* Parts of GraphicProducerWrapper are run on two different threads,
3115 * communicating by sending messages via Looper but also by shared member
3116 * data. Coherence maintenance is subtle and in places implicit (ugh).
3117 *
3118 * Don't rely on Looper's sendMessage/handleMessage providing
3119 * release/acquire semantics for any data not actually in the Message.
3120 * Data going from surfaceflinger to binder threads needs to be
3121 * synchronized explicitly.
3122 *
3123 * Barrier open/wait do provide release/acquire semantics. This provides
3124 * implicit synchronization for data coming back from binder to
3125 * surfaceflinger threads.
3126 */
3127
3128 sp<IGraphicBufferProducer> impl;
3129 sp<Looper> looper;
3130 status_t result;
3131 bool exitPending;
3132 bool exitRequested;
3133 Barrier barrier;
3134 uint32_t code;
3135 Parcel const* data;
3136 Parcel* reply;
3137
3138 enum {
3139 MSG_API_CALL,
3140 MSG_EXIT
3141 };
3142
3143 /*
3144 * Called on surfaceflinger thread. This is called by our "fake"
3145 * BpGraphicBufferProducer. We package the data and reply Parcel and
3146 * forward them to the binder thread.
3147 */
3148 virtual status_t transact(uint32_t code,
3149 const Parcel& data, Parcel* reply, uint32_t /* flags */) {
3150 this->code = code;
3151 this->data = &data;
3152 this->reply = reply;
3153 if (exitPending) {
3154 // if we've exited, we run the message synchronously right here.
3155 // note (JH): as far as I can tell from looking at the code, this
3156 // never actually happens. if it does, i'm not sure if it happens
3157 // on the surfaceflinger or binder thread.
3158 handleMessage(Message(MSG_API_CALL));
3159 } else {
3160 barrier.close();
3161 // Prevent stores to this->{code, data, reply} from being
3162 // reordered later than the construction of Message.
3163 atomic_thread_fence(memory_order_release);
3164 looper->sendMessage(this, Message(MSG_API_CALL));
3165 barrier.wait();
3166 }
3167 return result;
3168 }
3169
3170 /*
3171 * here we run on the binder thread. All we've got to do is
3172 * call the real BpGraphicBufferProducer.
3173 */
3174 virtual void handleMessage(const Message& message) {
3175 int what = message.what;
3176 // Prevent reads below from happening before the read from Message
3177 atomic_thread_fence(memory_order_acquire);
3178 if (what == MSG_API_CALL) {
3179 result = IInterface::asBinder(impl)->transact(code, data[0], reply);
3180 barrier.open();
3181 } else if (what == MSG_EXIT) {
3182 exitRequested = true;
3183 }
3184 }
3185
3186public:
3187 GraphicProducerWrapper(const sp<IGraphicBufferProducer>& impl)
3188 : impl(impl),
3189 looper(new Looper(true)),
3190 result(NO_ERROR),
3191 exitPending(false),
3192 exitRequested(false),
3193 code(0),
3194 data(NULL),
3195 reply(NULL)
3196 {}
3197
3198 // Binder thread
3199 status_t waitForResponse() {
3200 do {
3201 looper->pollOnce(-1);
3202 } while (!exitRequested);
3203 return result;
3204 }
3205
3206 // Client thread
3207 void exit(status_t result) {
3208 this->result = result;
3209 exitPending = true;
3210 // Ensure this->result is visible to the binder thread before it
3211 // handles the message.
3212 atomic_thread_fence(memory_order_release);
3213 looper->sendMessage(this, Message(MSG_EXIT));
3214 }
3215};
3216
3217
3218status_t SurfaceFlinger::captureScreen(const sp<IBinder>& display,
3219 const sp<IGraphicBufferProducer>& producer,
3220 Rect sourceCrop, uint32_t reqWidth, uint32_t reqHeight,
3221 uint32_t minLayerZ, uint32_t maxLayerZ,
3222 bool useIdentityTransform, ISurfaceComposer::Rotation rotation) {
3223
3224 if (CC_UNLIKELY(display == 0))
3225 return BAD_VALUE;
3226
3227 if (CC_UNLIKELY(producer == 0))
3228 return BAD_VALUE;
3229
3230 // if we have secure windows on this display, never allow the screen capture
3231 // unless the producer interface is local (i.e.: we can take a screenshot for
3232 // ourselves).
3233 bool isLocalScreenshot = IInterface::asBinder(producer)->localBinder();
3234
3235 // Convert to surfaceflinger's internal rotation type.
3236 Transform::orientation_flags rotationFlags;
3237 switch (rotation) {
3238 case ISurfaceComposer::eRotateNone:
3239 rotationFlags = Transform::ROT_0;
3240 break;
3241 case ISurfaceComposer::eRotate90:
3242 rotationFlags = Transform::ROT_90;
3243 break;
3244 case ISurfaceComposer::eRotate180:
3245 rotationFlags = Transform::ROT_180;
3246 break;
3247 case ISurfaceComposer::eRotate270:
3248 rotationFlags = Transform::ROT_270;
3249 break;
3250 default:
3251 rotationFlags = Transform::ROT_0;
3252 ALOGE("Invalid rotation passed to captureScreen(): %d\n", rotation);
3253 break;
3254 }
3255
3256 class MessageCaptureScreen : public MessageBase {
3257 SurfaceFlinger* flinger;
3258 sp<IBinder> display;
3259 sp<IGraphicBufferProducer> producer;
3260 Rect sourceCrop;
3261 uint32_t reqWidth, reqHeight;
3262 uint32_t minLayerZ,maxLayerZ;
3263 bool useIdentityTransform;
3264 Transform::orientation_flags rotation;
3265 status_t result;
3266 bool isLocalScreenshot;
3267 public:
3268 MessageCaptureScreen(SurfaceFlinger* flinger,
3269 const sp<IBinder>& display,
3270 const sp<IGraphicBufferProducer>& producer,
3271 Rect sourceCrop, uint32_t reqWidth, uint32_t reqHeight,
3272 uint32_t minLayerZ, uint32_t maxLayerZ,
3273 bool useIdentityTransform,
3274 Transform::orientation_flags rotation,
3275 bool isLocalScreenshot)
3276 : flinger(flinger), display(display), producer(producer),
3277 sourceCrop(sourceCrop), reqWidth(reqWidth), reqHeight(reqHeight),
3278 minLayerZ(minLayerZ), maxLayerZ(maxLayerZ),
3279 useIdentityTransform(useIdentityTransform),
3280 rotation(rotation), result(PERMISSION_DENIED),
3281 isLocalScreenshot(isLocalScreenshot)
3282 {
3283 }
3284 status_t getResult() const {
3285 return result;
3286 }
3287 virtual bool handler() {
3288 Mutex::Autolock _l(flinger->mStateLock);
3289 sp<const DisplayDevice> hw(flinger->getDisplayDevice(display));
3290 result = flinger->captureScreenImplLocked(hw, producer,
3291 sourceCrop, reqWidth, reqHeight, minLayerZ, maxLayerZ,
3292 useIdentityTransform, rotation, isLocalScreenshot);
3293 static_cast<GraphicProducerWrapper*>(IInterface::asBinder(producer).get())->exit(result);
3294 return true;
3295 }
3296 };
3297
3298 // make sure to process transactions before screenshots -- a transaction
3299 // might already be pending but scheduled for VSYNC; this guarantees we
3300 // will handle it before the screenshot. When VSYNC finally arrives
3301 // the scheduled transaction will be a no-op. If no transactions are
3302 // scheduled at this time, this will end-up being a no-op as well.
3303 mEventQueue.invalidateTransactionNow();
3304
3305 // this creates a "fake" BBinder which will serve as a "fake" remote
3306 // binder to receive the marshaled calls and forward them to the
3307 // real remote (a BpGraphicBufferProducer)
3308 sp<GraphicProducerWrapper> wrapper = new GraphicProducerWrapper(producer);
3309
3310 // the asInterface() call below creates our "fake" BpGraphicBufferProducer
3311 // which does the marshaling work forwards to our "fake remote" above.
3312 sp<MessageBase> msg = new MessageCaptureScreen(this,
3313 display, IGraphicBufferProducer::asInterface( wrapper ),
3314 sourceCrop, reqWidth, reqHeight, minLayerZ, maxLayerZ,
3315 useIdentityTransform, rotationFlags, isLocalScreenshot);
3316
3317 status_t res = postMessageAsync(msg);
3318 if (res == NO_ERROR) {
3319 res = wrapper->waitForResponse();
3320 }
3321 return res;
3322}
3323
3324
3325void SurfaceFlinger::renderScreenImplLocked(
3326 const sp<const DisplayDevice>& hw,
3327 Rect sourceCrop, uint32_t reqWidth, uint32_t reqHeight,
3328 uint32_t minLayerZ, uint32_t maxLayerZ,
3329 bool yswap, bool useIdentityTransform, Transform::orientation_flags rotation)
3330{
3331 ATRACE_CALL();
3332 RenderEngine& engine(getRenderEngine());
3333
3334 // get screen geometry
3335 const int32_t hw_w = hw->getWidth();
3336 const int32_t hw_h = hw->getHeight();
3337 const bool filtering = static_cast<int32_t>(reqWidth) != hw_w ||
3338 static_cast<int32_t>(reqHeight) != hw_h;
3339
3340 // if a default or invalid sourceCrop is passed in, set reasonable values
3341 if (sourceCrop.width() == 0 || sourceCrop.height() == 0 ||
3342 !sourceCrop.isValid()) {
3343 sourceCrop.setLeftTop(Point(0, 0));
3344 sourceCrop.setRightBottom(Point(hw_w, hw_h));
3345 }
3346
3347 // ensure that sourceCrop is inside screen
3348 if (sourceCrop.left < 0) {
3349 ALOGE("Invalid crop rect: l = %d (< 0)", sourceCrop.left);
3350 }
3351 if (sourceCrop.right > hw_w) {
3352 ALOGE("Invalid crop rect: r = %d (> %d)", sourceCrop.right, hw_w);
3353 }
3354 if (sourceCrop.top < 0) {
3355 ALOGE("Invalid crop rect: t = %d (< 0)", sourceCrop.top);
3356 }
3357 if (sourceCrop.bottom > hw_h) {
3358 ALOGE("Invalid crop rect: b = %d (> %d)", sourceCrop.bottom, hw_h);
3359 }
3360
3361 // make sure to clear all GL error flags
3362 engine.checkErrors();
3363
3364 // set-up our viewport
3365 engine.setViewportAndProjection(
3366 reqWidth, reqHeight, sourceCrop, hw_h, yswap, rotation);
3367 engine.disableTexturing();
3368
3369 // redraw the screen entirely...
3370 engine.clearWithColor(0, 0, 0, 1);
3371
3372 const LayerVector& layers( mDrawingState.layersSortedByZ );
3373 const size_t count = layers.size();
3374 for (size_t i=0 ; i<count ; ++i) {
3375 const sp<Layer>& layer(layers[i]);
3376 const Layer::State& state(layer->getDrawingState());
3377 if (state.layerStack == hw->getLayerStack()) {
3378 if (state.z >= minLayerZ && state.z <= maxLayerZ) {
3379 if (layer->isVisible()) {
3380 if (filtering) layer->setFiltering(true);
3381 layer->draw(hw, useIdentityTransform);
3382 if (filtering) layer->setFiltering(false);
3383 }
3384 }
3385 }
3386 }
3387
3388 // compositionComplete is needed for older driver
3389 hw->compositionComplete();
3390 hw->setViewportAndProjection();
3391}
3392
3393
3394status_t SurfaceFlinger::captureScreenImplLocked(
3395 const sp<const DisplayDevice>& hw,
3396 const sp<IGraphicBufferProducer>& producer,
3397 Rect sourceCrop, uint32_t reqWidth, uint32_t reqHeight,
3398 uint32_t minLayerZ, uint32_t maxLayerZ,
3399 bool useIdentityTransform, Transform::orientation_flags rotation,
3400 bool isLocalScreenshot)
3401{
3402 ATRACE_CALL();
3403
3404 // get screen geometry
3405 uint32_t hw_w = hw->getWidth();
3406 uint32_t hw_h = hw->getHeight();
3407
3408 if (rotation & Transform::ROT_90) {
3409 std::swap(hw_w, hw_h);
3410 }
3411
3412 if ((reqWidth > hw_w) || (reqHeight > hw_h)) {
3413 ALOGE("size mismatch (%d, %d) > (%d, %d)",
3414 reqWidth, reqHeight, hw_w, hw_h);
3415 return BAD_VALUE;
3416 }
3417
3418 reqWidth = (!reqWidth) ? hw_w : reqWidth;
3419 reqHeight = (!reqHeight) ? hw_h : reqHeight;
3420
3421 bool secureLayerIsVisible = false;
3422 const LayerVector& layers(mDrawingState.layersSortedByZ);
3423 const size_t count = layers.size();
3424 for (size_t i = 0 ; i < count ; ++i) {
3425 const sp<Layer>& layer(layers[i]);
3426 const Layer::State& state(layer->getDrawingState());
3427 if (state.layerStack == hw->getLayerStack() && state.z >= minLayerZ &&
3428 state.z <= maxLayerZ && layer->isVisible() &&
3429 layer->isSecure()) {
3430 secureLayerIsVisible = true;
3431 }
3432 }
3433
3434 if (!isLocalScreenshot && secureLayerIsVisible) {
3435 ALOGW("FB is protected: PERMISSION_DENIED");
3436 return PERMISSION_DENIED;
3437 }
3438
3439 // create a surface (because we're a producer, and we need to
3440 // dequeue/queue a buffer)
3441 sp<Surface> sur = new Surface(producer, false);
3442 ANativeWindow* window = sur.get();
3443
3444 status_t result = native_window_api_connect(window, NATIVE_WINDOW_API_EGL);
3445 if (result == NO_ERROR) {
3446 uint32_t usage = GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN |
3447 GRALLOC_USAGE_HW_RENDER | GRALLOC_USAGE_HW_TEXTURE;
3448
3449 int err = 0;
3450 err = native_window_set_buffers_dimensions(window, reqWidth, reqHeight);
3451 err |= native_window_set_scaling_mode(window, NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW);
3452 err |= native_window_set_buffers_format(window, HAL_PIXEL_FORMAT_RGBA_8888);
3453 err |= native_window_set_usage(window, usage);
3454
3455 if (err == NO_ERROR) {
3456 ANativeWindowBuffer* buffer;
3457 /* TODO: Once we have the sync framework everywhere this can use
3458 * server-side waits on the fence that dequeueBuffer returns.
3459 */
3460 result = native_window_dequeue_buffer_and_wait(window, &buffer);
3461 if (result == NO_ERROR) {
3462 int syncFd = -1;
3463 // create an EGLImage from the buffer so we can later
3464 // turn it into a texture
3465 EGLImageKHR image = eglCreateImageKHR(mEGLDisplay, EGL_NO_CONTEXT,
3466 EGL_NATIVE_BUFFER_ANDROID, buffer, NULL);
3467 if (image != EGL_NO_IMAGE_KHR) {
3468 // this binds the given EGLImage as a framebuffer for the
3469 // duration of this scope.
3470 RenderEngine::BindImageAsFramebuffer imageBond(getRenderEngine(), image);
3471 if (imageBond.getStatus() == NO_ERROR) {
3472 // this will in fact render into our dequeued buffer
3473 // via an FBO, which means we didn't have to create
3474 // an EGLSurface and therefore we're not
3475 // dependent on the context's EGLConfig.
3476 renderScreenImplLocked(
3477 hw, sourceCrop, reqWidth, reqHeight, minLayerZ, maxLayerZ, true,
3478 useIdentityTransform, rotation);
3479
3480 // Attempt to create a sync khr object that can produce a sync point. If that
3481 // isn't available, create a non-dupable sync object in the fallback path and
3482 // wait on it directly.
3483 EGLSyncKHR sync;
3484 if (!DEBUG_SCREENSHOTS) {
3485 sync = eglCreateSyncKHR(mEGLDisplay, EGL_SYNC_NATIVE_FENCE_ANDROID, NULL);
3486 // native fence fd will not be populated until flush() is done.
3487 getRenderEngine().flush();
3488 } else {
3489 sync = EGL_NO_SYNC_KHR;
3490 }
3491 if (sync != EGL_NO_SYNC_KHR) {
3492 // get the sync fd
3493 syncFd = eglDupNativeFenceFDANDROID(mEGLDisplay, sync);
3494 if (syncFd == EGL_NO_NATIVE_FENCE_FD_ANDROID) {
3495 ALOGW("captureScreen: failed to dup sync khr object");
3496 syncFd = -1;
3497 }
3498 eglDestroySyncKHR(mEGLDisplay, sync);
3499 } else {
3500 // fallback path
3501 sync = eglCreateSyncKHR(mEGLDisplay, EGL_SYNC_FENCE_KHR, NULL);
3502 if (sync != EGL_NO_SYNC_KHR) {
3503 EGLint result = eglClientWaitSyncKHR(mEGLDisplay, sync,
3504 EGL_SYNC_FLUSH_COMMANDS_BIT_KHR, 2000000000 /*2 sec*/);
3505 EGLint eglErr = eglGetError();
3506 if (result == EGL_TIMEOUT_EXPIRED_KHR) {
3507 ALOGW("captureScreen: fence wait timed out");
3508 } else {
3509 ALOGW_IF(eglErr != EGL_SUCCESS,
3510 "captureScreen: error waiting on EGL fence: %#x", eglErr);
3511 }
3512 eglDestroySyncKHR(mEGLDisplay, sync);
3513 } else {
3514 ALOGW("captureScreen: error creating EGL fence: %#x", eglGetError());
3515 }
3516 }
3517 if (DEBUG_SCREENSHOTS) {
3518 uint32_t* pixels = new uint32_t[reqWidth*reqHeight];
3519 getRenderEngine().readPixels(0, 0, reqWidth, reqHeight, pixels);
3520 checkScreenshot(reqWidth, reqHeight, reqWidth, pixels,
3521 hw, minLayerZ, maxLayerZ);
3522 delete [] pixels;
3523 }
3524
3525 } else {
3526 ALOGE("got GL_FRAMEBUFFER_COMPLETE_OES error while taking screenshot");
3527 result = INVALID_OPERATION;
Prathmesh Prabhuf3209b02016-03-09 16:54:45 -08003528 window->cancelBuffer(window, buffer, syncFd);
3529 buffer = NULL;
Dan Stoza9e56aa02015-11-02 13:00:03 -08003530 }
3531 // destroy our image
3532 eglDestroyImageKHR(mEGLDisplay, image);
3533 } else {
3534 result = BAD_VALUE;
3535 }
Prathmesh Prabhuf3209b02016-03-09 16:54:45 -08003536 if (buffer) {
3537 // queueBuffer takes ownership of syncFd
3538 result = window->queueBuffer(window, buffer, syncFd);
3539 }
Dan Stoza9e56aa02015-11-02 13:00:03 -08003540 }
3541 } else {
3542 result = BAD_VALUE;
3543 }
3544 native_window_api_disconnect(window, NATIVE_WINDOW_API_EGL);
3545 }
3546
3547 return result;
3548}
3549
3550void SurfaceFlinger::checkScreenshot(size_t w, size_t s, size_t h, void const* vaddr,
3551 const sp<const DisplayDevice>& hw, uint32_t minLayerZ, uint32_t maxLayerZ) {
3552 if (DEBUG_SCREENSHOTS) {
3553 for (size_t y=0 ; y<h ; y++) {
3554 uint32_t const * p = (uint32_t const *)vaddr + y*s;
3555 for (size_t x=0 ; x<w ; x++) {
3556 if (p[x] != 0xFF000000) return;
3557 }
3558 }
3559 ALOGE("*** we just took a black screenshot ***\n"
3560 "requested minz=%d, maxz=%d, layerStack=%d",
3561 minLayerZ, maxLayerZ, hw->getLayerStack());
3562 const LayerVector& layers( mDrawingState.layersSortedByZ );
3563 const size_t count = layers.size();
3564 for (size_t i=0 ; i<count ; ++i) {
3565 const sp<Layer>& layer(layers[i]);
3566 const Layer::State& state(layer->getDrawingState());
3567 const bool visible = (state.layerStack == hw->getLayerStack())
3568 && (state.z >= minLayerZ && state.z <= maxLayerZ)
3569 && (layer->isVisible());
3570 ALOGE("%c index=%zu, name=%s, layerStack=%d, z=%d, visible=%d, flags=%x, alpha=%x",
3571 visible ? '+' : '-',
3572 i, layer->getName().string(), state.layerStack, state.z,
3573 layer->isVisible(), state.flags, state.alpha);
3574 }
3575 }
3576}
3577
3578// ---------------------------------------------------------------------------
3579
3580SurfaceFlinger::LayerVector::LayerVector() {
3581}
3582
3583SurfaceFlinger::LayerVector::LayerVector(const LayerVector& rhs)
3584 : SortedVector<sp<Layer> >(rhs) {
3585}
3586
3587int SurfaceFlinger::LayerVector::do_compare(const void* lhs,
3588 const void* rhs) const
3589{
3590 // sort layers per layer-stack, then by z-order and finally by sequence
3591 const sp<Layer>& l(*reinterpret_cast<const sp<Layer>*>(lhs));
3592 const sp<Layer>& r(*reinterpret_cast<const sp<Layer>*>(rhs));
3593
3594 uint32_t ls = l->getCurrentState().layerStack;
3595 uint32_t rs = r->getCurrentState().layerStack;
3596 if (ls != rs)
3597 return ls - rs;
3598
3599 uint32_t lz = l->getCurrentState().z;
3600 uint32_t rz = r->getCurrentState().z;
3601 if (lz != rz)
3602 return lz - rz;
3603
3604 return l->sequence - r->sequence;
3605}
3606
3607// ---------------------------------------------------------------------------
3608
3609SurfaceFlinger::DisplayDeviceState::DisplayDeviceState()
3610 : type(DisplayDevice::DISPLAY_ID_INVALID),
3611 layerStack(DisplayDevice::NO_LAYER_STACK),
3612 orientation(0),
3613 width(0),
3614 height(0),
3615 isSecure(false) {
3616}
3617
3618SurfaceFlinger::DisplayDeviceState::DisplayDeviceState(
3619 DisplayDevice::DisplayType type, bool isSecure)
3620 : type(type),
3621 layerStack(DisplayDevice::NO_LAYER_STACK),
3622 orientation(0),
3623 width(0),
3624 height(0),
3625 isSecure(isSecure) {
3626 viewport.makeInvalid();
3627 frame.makeInvalid();
3628}
3629
3630// ---------------------------------------------------------------------------
3631
3632}; // namespace android
3633
3634
3635#if defined(__gl_h_)
3636#error "don't include gl/gl.h in this file"
3637#endif
3638
3639#if defined(__gl2_h_)
3640#error "don't include gl2/gl2.h in this file"
3641#endif