Add new Looper API to check whether the looper is idle.
This is just to support the watchdog to give it a faster way to determine if a thread is deadlocked without having to post a message to it. Change-Id: I068dc8b9387caf94fe5811fb4aeb0f9b57b1a080
This commit is contained in:
parent
779434378e
commit
ffad7d1fdc
@ -296,6 +296,13 @@ public:
|
|||||||
*/
|
*/
|
||||||
void removeMessages(const sp<MessageHandler>& handler, int what);
|
void removeMessages(const sp<MessageHandler>& handler, int what);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return whether this looper's thread is currently idling -- that is, whether it
|
||||||
|
* stopped waiting for more work to do. Note that this is intrinsically racy, since
|
||||||
|
* its state can change before you get the result back.
|
||||||
|
*/
|
||||||
|
bool isIdling() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Prepares a looper associated with the calling thread, and returns it.
|
* Prepares a looper associated with the calling thread, and returns it.
|
||||||
* If the thread already has a looper, it is returned. Otherwise, a new
|
* If the thread already has a looper, it is returned. Otherwise, a new
|
||||||
@ -353,6 +360,10 @@ private:
|
|||||||
Vector<MessageEnvelope> mMessageEnvelopes; // guarded by mLock
|
Vector<MessageEnvelope> mMessageEnvelopes; // guarded by mLock
|
||||||
bool mSendingMessage; // guarded by mLock
|
bool mSendingMessage; // guarded by mLock
|
||||||
|
|
||||||
|
// Whether we are currently waiting for work. Not protected by a lock,
|
||||||
|
// any use of it is racy anyway.
|
||||||
|
volatile bool mIdling;
|
||||||
|
|
||||||
int mEpollFd; // immutable
|
int mEpollFd; // immutable
|
||||||
|
|
||||||
// Locked list of file descriptor monitoring requests.
|
// Locked list of file descriptor monitoring requests.
|
||||||
|
@ -84,6 +84,8 @@ Looper::Looper(bool allowNonCallbacks) :
|
|||||||
LOG_ALWAYS_FATAL_IF(result != 0, "Could not make wake write pipe non-blocking. errno=%d",
|
LOG_ALWAYS_FATAL_IF(result != 0, "Could not make wake write pipe non-blocking. errno=%d",
|
||||||
errno);
|
errno);
|
||||||
|
|
||||||
|
mIdling = false;
|
||||||
|
|
||||||
// Allocate the epoll instance and register the wake pipe.
|
// Allocate the epoll instance and register the wake pipe.
|
||||||
mEpollFd = epoll_create(EPOLL_SIZE_HINT);
|
mEpollFd = epoll_create(EPOLL_SIZE_HINT);
|
||||||
LOG_ALWAYS_FATAL_IF(mEpollFd < 0, "Could not create epoll instance. errno=%d", errno);
|
LOG_ALWAYS_FATAL_IF(mEpollFd < 0, "Could not create epoll instance. errno=%d", errno);
|
||||||
@ -214,9 +216,15 @@ int Looper::pollInner(int timeoutMillis) {
|
|||||||
mResponses.clear();
|
mResponses.clear();
|
||||||
mResponseIndex = 0;
|
mResponseIndex = 0;
|
||||||
|
|
||||||
|
// We are about to idle.
|
||||||
|
mIdling = true;
|
||||||
|
|
||||||
struct epoll_event eventItems[EPOLL_MAX_EVENTS];
|
struct epoll_event eventItems[EPOLL_MAX_EVENTS];
|
||||||
int eventCount = epoll_wait(mEpollFd, eventItems, EPOLL_MAX_EVENTS, timeoutMillis);
|
int eventCount = epoll_wait(mEpollFd, eventItems, EPOLL_MAX_EVENTS, timeoutMillis);
|
||||||
|
|
||||||
|
// No longer idling.
|
||||||
|
mIdling = false;
|
||||||
|
|
||||||
// Acquire lock.
|
// Acquire lock.
|
||||||
mLock.lock();
|
mLock.lock();
|
||||||
|
|
||||||
@ -558,4 +566,8 @@ void Looper::removeMessages(const sp<MessageHandler>& handler, int what) {
|
|||||||
} // release lock
|
} // release lock
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool Looper::isIdling() const {
|
||||||
|
return mIdling;
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace android
|
} // namespace android
|
||||||
|
Loading…
Reference in New Issue
Block a user