diff --git a/services/surfaceflinger/DisplayDevice.cpp b/services/surfaceflinger/DisplayDevice.cpp index a33b94bd3..18119f692 100644 --- a/services/surfaceflinger/DisplayDevice.cpp +++ b/services/surfaceflinger/DisplayDevice.cpp @@ -117,12 +117,10 @@ DisplayDevice::DisplayDevice( mSurface(EGL_NO_SURFACE), mContext(EGL_NO_CONTEXT), mDpiX(), mDpiY(), - mRefreshRate(), mDensity(), mDisplayWidth(), mDisplayHeight(), mFormat(), mFlags(), mPageFlipCount(), - mRefreshPeriod(), mSecureLayerVisible(false), mScreenAcquired(false), mOrientation(), @@ -160,10 +158,6 @@ float DisplayDevice::getDensity() const { return mDensity; } -float DisplayDevice::getRefreshRate() const { - return mRefreshRate; -} - int DisplayDevice::getWidth() const { return mDisplayWidth; } @@ -180,19 +174,6 @@ EGLSurface DisplayDevice::getEGLSurface() const { return mSurface; } -status_t DisplayDevice::getInfo(DisplayInfo* info) const { - info->w = getWidth(); - info->h = getHeight(); - info->xdpi = getDpiX(); - info->ydpi = getDpiY(); - info->fps = getRefreshRate(); - info->density = getDensity(); - info->orientation = getOrientation(); - // TODO: this needs to go away (currently needed only by webkit) - getPixelFormatInfo(getFormat(), &info->pixelFormatInfo); - return NO_ERROR; -} - void DisplayDevice::init(EGLConfig config) { ANativeWindow* const window = mNativeWindow.get(); @@ -207,13 +188,6 @@ void DisplayDevice::init(EGLConfig config) window->query(window, NATIVE_WINDOW_FORMAT, &format); mDpiX = window->xdpi; mDpiY = window->ydpi; - if (mFramebufferSurface != NULL) { - mRefreshRate = mFramebufferSurface->getRefreshRate(); - } else { - mRefreshRate = 60; - } - mRefreshPeriod = nsecs_t(1e9 / mRefreshRate); - // TODO: Not sure if display density should handled by SF any longer class Density { @@ -279,10 +253,6 @@ uint32_t DisplayDevice::getPageFlipCount() const { return mPageFlipCount; } -nsecs_t DisplayDevice::getRefreshPeriod() const { - return mRefreshPeriod; -} - status_t DisplayDevice::compositionComplete() const { if (mFramebufferSurface == NULL) { return NO_ERROR; diff --git a/services/surfaceflinger/DisplayDevice.h b/services/surfaceflinger/DisplayDevice.h index 96590a001..d7aa6fb68 100644 --- a/services/surfaceflinger/DisplayDevice.h +++ b/services/surfaceflinger/DisplayDevice.h @@ -82,14 +82,11 @@ public: float getDpiX() const; float getDpiY() const; - float getRefreshRate() const; float getDensity() const; int getWidth() const; int getHeight() const; PixelFormat getFormat() const; uint32_t getFlags() const; - nsecs_t getRefreshPeriod() const; - status_t getInfo(DisplayInfo* info) const; EGLSurface getEGLSurface() const; @@ -149,14 +146,12 @@ private: EGLContext mContext; float mDpiX; float mDpiY; - float mRefreshRate; float mDensity; int mDisplayWidth; int mDisplayHeight; PixelFormat mFormat; uint32_t mFlags; mutable uint32_t mPageFlipCount; - nsecs_t mRefreshPeriod; /* * Can only accessed from the main thread, these members diff --git a/services/surfaceflinger/DisplayHardware/HWComposer.cpp b/services/surfaceflinger/DisplayHardware/HWComposer.cpp index d3378058d..2a51fb66c 100644 --- a/services/surfaceflinger/DisplayHardware/HWComposer.cpp +++ b/services/surfaceflinger/DisplayHardware/HWComposer.cpp @@ -101,14 +101,12 @@ struct HWComposer::cb_context { HWComposer::HWComposer( const sp& flinger, - EventHandler& handler, - nsecs_t refreshPeriod) + EventHandler& handler) : mFlinger(flinger), mModule(0), mHwc(0), mList(0), mCapacity(0), mNumOVLayers(0), mNumFBLayers(0), mCBContext(new cb_context), - mEventHandler(handler), - mRefreshPeriod(refreshPeriod), + mEventHandler(handler), mRefreshPeriod(0), mVSyncCount(0), mDebugForceFakeVSync(false) { char value[PROPERTY_VALUE_MAX]; @@ -137,6 +135,11 @@ HWComposer::HWComposer( // always turn vsync off when we start mHwc->methods->eventControl(mHwc, HWC_EVENT_VSYNC, 0); needVSyncThread = false; + + int period; + if (mHwc->query(mHwc, HWC_VSYNC_PERIOD, &period) == NO_ERROR) { + mRefreshPeriod = nsecs_t(period); + } } if (mHwc->registerProcs) { mCBContext->hwc = this; @@ -148,6 +151,26 @@ HWComposer::HWComposer( } } + if (mRefreshPeriod == 0) { + // for compatibility, we attempt to get the refresh rate from + // the FB HAL if we couldn't get it from the HWC HAL. + hw_module_t const* module; + if (hw_get_module(GRALLOC_HARDWARE_MODULE_ID, &module) == 0) { + framebuffer_device_t* fbDev; + int err = framebuffer_open(module, &fbDev); + if (!err && fbDev) { + mRefreshPeriod = nsecs_t(1e9 / fbDev->fps); + framebuffer_close(fbDev); + } + } + ALOGW("getting VSYNC period from fb HAL: %lld", mRefreshPeriod); + } + + if (mRefreshPeriod == 0) { + mRefreshPeriod = nsecs_t(1e9 / 60.0); + ALOGW("getting VSYNC period thin air: %lld", mRefreshPeriod); + } + if (needVSyncThread) { // we don't have VSYNC support, we need to fake it mVSyncThread = new VSyncThread(*this); @@ -189,6 +212,10 @@ void HWComposer::vsync(int dpy, int64_t timestamp) { mLastHwVSync = timestamp; } +nsecs_t HWComposer::getRefreshPeriod() const { + return mRefreshPeriod; +} + nsecs_t HWComposer::getRefreshTimestamp() const { // this returns the last refresh timestamp. // if the last one is not available, we estimate it based on diff --git a/services/surfaceflinger/DisplayHardware/HWComposer.h b/services/surfaceflinger/DisplayHardware/HWComposer.h index 872ab98e5..b9c93371e 100644 --- a/services/surfaceflinger/DisplayHardware/HWComposer.h +++ b/services/surfaceflinger/DisplayHardware/HWComposer.h @@ -55,8 +55,7 @@ public: virtual ~EventHandler() {} }; - HWComposer(const sp& flinger, - EventHandler& handler, nsecs_t refreshPeriod); + HWComposer(const sp& flinger, EventHandler& handler); ~HWComposer(); status_t initCheck() const; @@ -189,6 +188,7 @@ public: void eventControl(int event, int enabled); + nsecs_t getRefreshPeriod() const; nsecs_t getRefreshTimestamp() const; // this class is only used to fake the VSync event on systems that don't diff --git a/services/surfaceflinger/Layer.cpp b/services/surfaceflinger/Layer.cpp index 7da0c9bbf..f72000fde 100644 --- a/services/surfaceflinger/Layer.cpp +++ b/services/surfaceflinger/Layer.cpp @@ -729,7 +729,7 @@ void Layer::dumpStats(String8& result, char* buffer, size_t SIZE) const LayerBaseClient::dumpStats(result, buffer, SIZE); const size_t o = mFrameLatencyOffset; const DisplayDevice& hw(mFlinger->getDefaultDisplayDevice()); - const nsecs_t period = hw.getRefreshPeriod(); + const nsecs_t period = mFlinger->getHwComposer().getRefreshPeriod(); result.appendFormat("%lld\n", period); for (size_t i=0 ; i<128 ; i++) { const size_t index = (o+i) % 128; diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp index 382e01346..3aba3dbb8 100644 --- a/services/surfaceflinger/SurfaceFlinger.cpp +++ b/services/surfaceflinger/SurfaceFlinger.cpp @@ -378,9 +378,7 @@ status_t SurfaceFlinger::readyToRun() mEventQueue.setEventThread(mEventThread); // initialize the H/W composer - mHwc = new HWComposer(this, - *static_cast(this), - hw.getRefreshPeriod()); + mHwc = new HWComposer(this, *static_cast(this)); // initialize our drawing state mDrawingState = mCurrentState; @@ -453,11 +451,21 @@ bool SurfaceFlinger::authenticateSurfaceTexture( } status_t SurfaceFlinger::getDisplayInfo(DisplayID dpy, DisplayInfo* info) { + // TODO: this is here only for compatibility -- show go away eventually. if (uint32_t(dpy) >= 2) { return BAD_INDEX; } const DisplayDevice& hw(getDefaultDisplayDevice()); - return hw.getInfo(info); + info->w = hw.getWidth(); + info->h = hw.getHeight(); + info->xdpi = hw.getDpiX(); + info->ydpi = hw.getDpiY(); + info->fps = float(1e9 / getHwComposer().getRefreshPeriod()); + info->density = hw.getDensity(); + info->orientation = hw.getOrientation(); + // TODO: this needs to go away (currently needed only by webkit) + getPixelFormatInfo(hw.getFormat(), &info->pixelFormatInfo); + return NO_ERROR; } // ---------------------------------------------------------------------------- @@ -1818,6 +1826,7 @@ void SurfaceFlinger::dumpAllLocked( snprintf(buffer, SIZE, "SurfaceFlinger global state:\n"); result.append(buffer); + HWComposer& hwc(getHwComposer()); const DisplayDevice& hw(getDefaultDisplayDevice()); const GLExtensions& extensions(GLExtensions::getInstance()); snprintf(buffer, SIZE, "GLES: %s, %s, %s\n", @@ -1849,7 +1858,7 @@ void SurfaceFlinger::dumpAllLocked( mLastSwapBufferTime/1000.0, mLastTransactionTime/1000.0, mTransactionFlags, - hw.getRefreshRate(), + 1e9 / hwc.getRefreshPeriod(), hw.getDpiX(), hw.getDpiY(), hw.getDensity()); @@ -1871,7 +1880,6 @@ void SurfaceFlinger::dumpAllLocked( /* * Dump HWComposer state */ - HWComposer& hwc(getHwComposer()); snprintf(buffer, SIZE, "h/w composer state:\n"); result.append(buffer); snprintf(buffer, SIZE, " h/w composer %s and %s\n", diff --git a/services/surfaceflinger/SurfaceFlinger.h b/services/surfaceflinger/SurfaceFlinger.h index 6f224b62c..feeccf65f 100644 --- a/services/surfaceflinger/SurfaceFlinger.h +++ b/services/surfaceflinger/SurfaceFlinger.h @@ -336,7 +336,7 @@ private: HWComposer& getHwComposer() const { return *mHwc; } - /* ------------------------------------------------------------------------ + /* ------------------------------------------------------------------------ * Compositing */ void invalidateHwcGeometry();