Loading services/surfaceflinger/EventThread.cpp +34 −9 Original line number Original line Diff line number Diff line Loading @@ -140,6 +140,8 @@ bool EventThread::threadLoop() { return true; return true; } } // This will return when (1) a vsync event has been received, and (2) there was // at least one connection interested in receiving it when we started waiting. Vector< sp<EventThread::Connection> > EventThread::waitForEvent( Vector< sp<EventThread::Connection> > EventThread::waitForEvent( DisplayEventReceiver::Event* event) DisplayEventReceiver::Event* event) { { Loading Loading @@ -193,31 +195,54 @@ Vector< sp<EventThread::Connection> > EventThread::waitForEvent( // don't report it, and disable VSYNC events // don't report it, and disable VSYNC events disableVSyncLocked(); disableVSyncLocked(); } else if (!timestamp && waitForVSync) { } else if (!timestamp && waitForVSync) { // we have at least one client, so we want vsync enabled // (TODO: this function is called right after we finish // notifying clients of a vsync, so this call will be made // at the vsync rate, e.g. 60fps. If we can accurately // track the current state we could avoid making this call // so often.) enableVSyncLocked(); enableVSyncLocked(); } } // note: !timestamp implies signalConnections.isEmpty() // note: !timestamp implies signalConnections.isEmpty(), because we // don't populate signalConnections if there's no vsync pending if (!timestamp) { if (!timestamp) { // wait for something to happen // wait for something to happen if (CC_UNLIKELY(mUseSoftwareVSync && waitForVSync)) { if (waitForVSync) { // h/w vsync cannot be used (screen is off), so we use // This is where we spend most of our time, waiting // a timeout instead. it doesn't matter how imprecise this // for vsync events and new client registrations. // is, we just need to make sure to serve the clients // if (mCondition.waitRelative(mLock, ms2ns(16)) == TIMED_OUT) { // If the screen is off, we can't use h/w vsync, so we // use a 16ms timeout instead. It doesn't need to be // precise, we just need to keep feeding our clients. // // We don't want to stall if there's a driver bug, so we // use a (long) timeout when waiting for h/w vsync, and // generate fake events when necessary. bool softwareSync = mUseSoftwareVSync; nsecs_t timeout = softwareSync ? ms2ns(16) : ms2ns(1000); if (mCondition.waitRelative(mLock, timeout) == TIMED_OUT) { if (!softwareSync) { ALOGW("Timed out waiting for hw vsync; faking it"); } mVSyncTimestamp = systemTime(SYSTEM_TIME_MONOTONIC); mVSyncTimestamp = systemTime(SYSTEM_TIME_MONOTONIC); mVSyncCount++; mVSyncCount++; } } } else { } else { // This is where we spend most of our time, waiting // Nobody is interested in vsync, so we just want to sleep. // for a vsync events and registered clients // h/w vsync should be disabled, so this will wait until we // get a new connection, or an existing connection becomes // interested in receiving vsync again. mCondition.wait(mLock); mCondition.wait(mLock); } } } } } while (signalConnections.isEmpty()); } while (signalConnections.isEmpty()); // here we're guaranteed to have a timestamp and some connections to signal // here we're guaranteed to have a timestamp and some connections to signal // (The connections might have dropped out of mDisplayEventConnections // while we were asleep, but we'll still have strong references to them.) // dispatch vsync events to listeners... // fill in vsync event info event->header.type = DisplayEventReceiver::DISPLAY_EVENT_VSYNC; event->header.type = DisplayEventReceiver::DISPLAY_EVENT_VSYNC; event->header.timestamp = timestamp; event->header.timestamp = timestamp; event->vsync.count = vsyncCount; event->vsync.count = vsyncCount; Loading Loading
services/surfaceflinger/EventThread.cpp +34 −9 Original line number Original line Diff line number Diff line Loading @@ -140,6 +140,8 @@ bool EventThread::threadLoop() { return true; return true; } } // This will return when (1) a vsync event has been received, and (2) there was // at least one connection interested in receiving it when we started waiting. Vector< sp<EventThread::Connection> > EventThread::waitForEvent( Vector< sp<EventThread::Connection> > EventThread::waitForEvent( DisplayEventReceiver::Event* event) DisplayEventReceiver::Event* event) { { Loading Loading @@ -193,31 +195,54 @@ Vector< sp<EventThread::Connection> > EventThread::waitForEvent( // don't report it, and disable VSYNC events // don't report it, and disable VSYNC events disableVSyncLocked(); disableVSyncLocked(); } else if (!timestamp && waitForVSync) { } else if (!timestamp && waitForVSync) { // we have at least one client, so we want vsync enabled // (TODO: this function is called right after we finish // notifying clients of a vsync, so this call will be made // at the vsync rate, e.g. 60fps. If we can accurately // track the current state we could avoid making this call // so often.) enableVSyncLocked(); enableVSyncLocked(); } } // note: !timestamp implies signalConnections.isEmpty() // note: !timestamp implies signalConnections.isEmpty(), because we // don't populate signalConnections if there's no vsync pending if (!timestamp) { if (!timestamp) { // wait for something to happen // wait for something to happen if (CC_UNLIKELY(mUseSoftwareVSync && waitForVSync)) { if (waitForVSync) { // h/w vsync cannot be used (screen is off), so we use // This is where we spend most of our time, waiting // a timeout instead. it doesn't matter how imprecise this // for vsync events and new client registrations. // is, we just need to make sure to serve the clients // if (mCondition.waitRelative(mLock, ms2ns(16)) == TIMED_OUT) { // If the screen is off, we can't use h/w vsync, so we // use a 16ms timeout instead. It doesn't need to be // precise, we just need to keep feeding our clients. // // We don't want to stall if there's a driver bug, so we // use a (long) timeout when waiting for h/w vsync, and // generate fake events when necessary. bool softwareSync = mUseSoftwareVSync; nsecs_t timeout = softwareSync ? ms2ns(16) : ms2ns(1000); if (mCondition.waitRelative(mLock, timeout) == TIMED_OUT) { if (!softwareSync) { ALOGW("Timed out waiting for hw vsync; faking it"); } mVSyncTimestamp = systemTime(SYSTEM_TIME_MONOTONIC); mVSyncTimestamp = systemTime(SYSTEM_TIME_MONOTONIC); mVSyncCount++; mVSyncCount++; } } } else { } else { // This is where we spend most of our time, waiting // Nobody is interested in vsync, so we just want to sleep. // for a vsync events and registered clients // h/w vsync should be disabled, so this will wait until we // get a new connection, or an existing connection becomes // interested in receiving vsync again. mCondition.wait(mLock); mCondition.wait(mLock); } } } } } while (signalConnections.isEmpty()); } while (signalConnections.isEmpty()); // here we're guaranteed to have a timestamp and some connections to signal // here we're guaranteed to have a timestamp and some connections to signal // (The connections might have dropped out of mDisplayEventConnections // while we were asleep, but we'll still have strong references to them.) // dispatch vsync events to listeners... // fill in vsync event info event->header.type = DisplayEventReceiver::DISPLAY_EVENT_VSYNC; event->header.type = DisplayEventReceiver::DISPLAY_EVENT_VSYNC; event->header.timestamp = timestamp; event->header.timestamp = timestamp; event->vsync.count = vsyncCount; event->vsync.count = vsyncCount; Loading