Home | History | Annotate | Download | only in libutils
      1 //
      2 // Copyright 2010 The Android Open Source Project
      3 //
      4 // A looper implementation based on epoll().
      5 //
      6 #define LOG_TAG "Looper"
      7 
      8 //#define LOG_NDEBUG 0
      9 
     10 // Debugs poll and wake interactions.
     11 #define DEBUG_POLL_AND_WAKE 0
     12 
     13 // Debugs callback registration and invocation.
     14 #define DEBUG_CALLBACKS 0
     15 
     16 #include <cutils/log.h>
     17 #include <utils/Looper.h>
     18 #include <utils/Timers.h>
     19 
     20 #include <unistd.h>
     21 #include <fcntl.h>
     22 #include <limits.h>
     23 #include <inttypes.h>
     24 #include <sys/eventfd.h>
     25 
     26 
     27 namespace android {
     28 
     29 // --- WeakMessageHandler ---
     30 
     31 WeakMessageHandler::WeakMessageHandler(const wp<MessageHandler>& handler) :
     32         mHandler(handler) {
     33 }
     34 
     35 WeakMessageHandler::~WeakMessageHandler() {
     36 }
     37 
     38 void WeakMessageHandler::handleMessage(const Message& message) {
     39     sp<MessageHandler> handler = mHandler.promote();
     40     if (handler != NULL) {
     41         handler->handleMessage(message);
     42     }
     43 }
     44 
     45 
     46 // --- SimpleLooperCallback ---
     47 
     48 SimpleLooperCallback::SimpleLooperCallback(Looper_callbackFunc callback) :
     49         mCallback(callback) {
     50 }
     51 
     52 SimpleLooperCallback::~SimpleLooperCallback() {
     53 }
     54 
     55 int SimpleLooperCallback::handleEvent(int fd, int events, void* data) {
     56     return mCallback(fd, events, data);
     57 }
     58 
     59 
     60 // --- Looper ---
     61 
     62 // Hint for number of file descriptors to be associated with the epoll instance.
     63 static const int EPOLL_SIZE_HINT = 8;
     64 
     65 // Maximum number of file descriptors for which to retrieve poll events each iteration.
     66 static const int EPOLL_MAX_EVENTS = 16;
     67 
     68 static pthread_once_t gTLSOnce = PTHREAD_ONCE_INIT;
     69 static pthread_key_t gTLSKey = 0;
     70 
     71 Looper::Looper(bool allowNonCallbacks) :
     72         mAllowNonCallbacks(allowNonCallbacks), mSendingMessage(false),
     73         mPolling(false), mEpollFd(-1), mEpollRebuildRequired(false),
     74         mNextRequestSeq(0), mResponseIndex(0), mNextMessageUptime(LLONG_MAX) {
     75     mWakeEventFd = eventfd(0, EFD_NONBLOCK);
     76     LOG_ALWAYS_FATAL_IF(mWakeEventFd < 0, "Could not make wake event fd.  errno=%d", errno);
     77 
     78     AutoMutex _l(mLock);
     79     rebuildEpollLocked();
     80 }
     81 
     82 Looper::~Looper() {
     83     close(mWakeEventFd);
     84     if (mEpollFd >= 0) {
     85         close(mEpollFd);
     86     }
     87 }
     88 
     89 void Looper::initTLSKey() {
     90     int result = pthread_key_create(& gTLSKey, threadDestructor);
     91     LOG_ALWAYS_FATAL_IF(result != 0, "Could not allocate TLS key.");
     92 }
     93 
     94 void Looper::threadDestructor(void *st) {
     95     Looper* const self = static_cast<Looper*>(st);
     96     if (self != NULL) {
     97         self->decStrong((void*)threadDestructor);
     98     }
     99 }
    100 
    101 void Looper::setForThread(const sp<Looper>& looper) {
    102     sp<Looper> old = getForThread(); // also has side-effect of initializing TLS
    103 
    104     if (looper != NULL) {
    105         looper->incStrong((void*)threadDestructor);
    106     }
    107 
    108     pthread_setspecific(gTLSKey, looper.get());
    109 
    110     if (old != NULL) {
    111         old->decStrong((void*)threadDestructor);
    112     }
    113 }
    114 
    115 sp<Looper> Looper::getForThread() {
    116     int result = pthread_once(& gTLSOnce, initTLSKey);
    117     LOG_ALWAYS_FATAL_IF(result != 0, "pthread_once failed");
    118 
    119     return (Looper*)pthread_getspecific(gTLSKey);
    120 }
    121 
    122 sp<Looper> Looper::prepare(int opts) {
    123     bool allowNonCallbacks = opts & PREPARE_ALLOW_NON_CALLBACKS;
    124     sp<Looper> looper = Looper::getForThread();
    125     if (looper == NULL) {
    126         looper = new Looper(allowNonCallbacks);
    127         Looper::setForThread(looper);
    128     }
    129     if (looper->getAllowNonCallbacks() != allowNonCallbacks) {
    130         ALOGW("Looper already prepared for this thread with a different value for the "
    131                 "LOOPER_PREPARE_ALLOW_NON_CALLBACKS option.");
    132     }
    133     return looper;
    134 }
    135 
    136 bool Looper::getAllowNonCallbacks() const {
    137     return mAllowNonCallbacks;
    138 }
    139 
    140 void Looper::rebuildEpollLocked() {
    141     // Close old epoll instance if we have one.
    142     if (mEpollFd >= 0) {
    143 #if DEBUG_CALLBACKS
    144         ALOGD("%p ~ rebuildEpollLocked - rebuilding epoll set", this);
    145 #endif
    146         close(mEpollFd);
    147     }
    148 
    149     // Allocate the new epoll instance and register the wake pipe.
    150     mEpollFd = epoll_create(EPOLL_SIZE_HINT);
    151     LOG_ALWAYS_FATAL_IF(mEpollFd < 0, "Could not create epoll instance.  errno=%d", errno);
    152 
    153     struct epoll_event eventItem;
    154     memset(& eventItem, 0, sizeof(epoll_event)); // zero out unused members of data field union
    155     eventItem.events = EPOLLIN;
    156     eventItem.data.fd = mWakeEventFd;
    157     int result = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, mWakeEventFd, & eventItem);
    158     LOG_ALWAYS_FATAL_IF(result != 0, "Could not add wake event fd to epoll instance.  errno=%d",
    159             errno);
    160 
    161     for (size_t i = 0; i < mRequests.size(); i++) {
    162         const Request& request = mRequests.valueAt(i);
    163         struct epoll_event eventItem;
    164         request.initEventItem(&eventItem);
    165 
    166         int epollResult = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, request.fd, & eventItem);
    167         if (epollResult < 0) {
    168             ALOGE("Error adding epoll events for fd %d while rebuilding epoll set, errno=%d",
    169                     request.fd, errno);
    170         }
    171     }
    172 }
    173 
    174 void Looper::scheduleEpollRebuildLocked() {
    175     if (!mEpollRebuildRequired) {
    176 #if DEBUG_CALLBACKS
    177         ALOGD("%p ~ scheduleEpollRebuildLocked - scheduling epoll set rebuild", this);
    178 #endif
    179         mEpollRebuildRequired = true;
    180         wake();
    181     }
    182 }
    183 
    184 int Looper::pollOnce(int timeoutMillis, int* outFd, int* outEvents, void** outData) {
    185     int result = 0;
    186     for (;;) {
    187         while (mResponseIndex < mResponses.size()) {
    188             const Response& response = mResponses.itemAt(mResponseIndex++);
    189             int ident = response.request.ident;
    190             if (ident >= 0) {
    191                 int fd = response.request.fd;
    192                 int events = response.events;
    193                 void* data = response.request.data;
    194 #if DEBUG_POLL_AND_WAKE
    195                 ALOGD("%p ~ pollOnce - returning signalled identifier %d: "
    196                         "fd=%d, events=0x%x, data=%p",
    197                         this, ident, fd, events, data);
    198 #endif
    199                 if (outFd != NULL) *outFd = fd;
    200                 if (outEvents != NULL) *outEvents = events;
    201                 if (outData != NULL) *outData = data;
    202                 return ident;
    203             }
    204         }
    205 
    206         if (result != 0) {
    207 #if DEBUG_POLL_AND_WAKE
    208             ALOGD("%p ~ pollOnce - returning result %d", this, result);
    209 #endif
    210             if (outFd != NULL) *outFd = 0;
    211             if (outEvents != NULL) *outEvents = 0;
    212             if (outData != NULL) *outData = NULL;
    213             return result;
    214         }
    215 
    216         result = pollInner(timeoutMillis);
    217     }
    218 }
    219 
    220 int Looper::pollInner(int timeoutMillis) {
    221 #if DEBUG_POLL_AND_WAKE
    222     ALOGD("%p ~ pollOnce - waiting: timeoutMillis=%d", this, timeoutMillis);
    223 #endif
    224 
    225     // Adjust the timeout based on when the next message is due.
    226     if (timeoutMillis != 0 && mNextMessageUptime != LLONG_MAX) {
    227         nsecs_t now = systemTime(SYSTEM_TIME_MONOTONIC);
    228         int messageTimeoutMillis = toMillisecondTimeoutDelay(now, mNextMessageUptime);
    229         if (messageTimeoutMillis >= 0
    230                 && (timeoutMillis < 0 || messageTimeoutMillis < timeoutMillis)) {
    231             timeoutMillis = messageTimeoutMillis;
    232         }
    233 #if DEBUG_POLL_AND_WAKE
    234         ALOGD("%p ~ pollOnce - next message in %" PRId64 "ns, adjusted timeout: timeoutMillis=%d",
    235                 this, mNextMessageUptime - now, timeoutMillis);
    236 #endif
    237     }
    238 
    239     // Poll.
    240     int result = POLL_WAKE;
    241     mResponses.clear();
    242     mResponseIndex = 0;
    243 
    244     // We are about to idle.
    245     mPolling = true;
    246 
    247     struct epoll_event eventItems[EPOLL_MAX_EVENTS];
    248     int eventCount = epoll_wait(mEpollFd, eventItems, EPOLL_MAX_EVENTS, timeoutMillis);
    249 
    250     // No longer idling.
    251     mPolling = false;
    252 
    253     // Acquire lock.
    254     mLock.lock();
    255 
    256     // Rebuild epoll set if needed.
    257     if (mEpollRebuildRequired) {
    258         mEpollRebuildRequired = false;
    259         rebuildEpollLocked();
    260         goto Done;
    261     }
    262 
    263     // Check for poll error.
    264     if (eventCount < 0) {
    265         if (errno == EINTR) {
    266             goto Done;
    267         }
    268         ALOGW("Poll failed with an unexpected error, errno=%d", errno);
    269         result = POLL_ERROR;
    270         goto Done;
    271     }
    272 
    273     // Check for poll timeout.
    274     if (eventCount == 0) {
    275 #if DEBUG_POLL_AND_WAKE
    276         ALOGD("%p ~ pollOnce - timeout", this);
    277 #endif
    278         result = POLL_TIMEOUT;
    279         goto Done;
    280     }
    281 
    282     // Handle all events.
    283 #if DEBUG_POLL_AND_WAKE
    284     ALOGD("%p ~ pollOnce - handling events from %d fds", this, eventCount);
    285 #endif
    286 
    287     for (int i = 0; i < eventCount; i++) {
    288         int fd = eventItems[i].data.fd;
    289         uint32_t epollEvents = eventItems[i].events;
    290         if (fd == mWakeEventFd) {
    291             if (epollEvents & EPOLLIN) {
    292                 awoken();
    293             } else {
    294                 ALOGW("Ignoring unexpected epoll events 0x%x on wake event fd.", epollEvents);
    295             }
    296         } else {
    297             ssize_t requestIndex = mRequests.indexOfKey(fd);
    298             if (requestIndex >= 0) {
    299                 int events = 0;
    300                 if (epollEvents & EPOLLIN) events |= EVENT_INPUT;
    301                 if (epollEvents & EPOLLOUT) events |= EVENT_OUTPUT;
    302                 if (epollEvents & EPOLLERR) events |= EVENT_ERROR;
    303                 if (epollEvents & EPOLLHUP) events |= EVENT_HANGUP;
    304                 pushResponse(events, mRequests.valueAt(requestIndex));
    305             } else {
    306                 ALOGW("Ignoring unexpected epoll events 0x%x on fd %d that is "
    307                         "no longer registered.", epollEvents, fd);
    308             }
    309         }
    310     }
    311 Done: ;
    312 
    313     // Invoke pending message callbacks.
    314     mNextMessageUptime = LLONG_MAX;
    315     while (mMessageEnvelopes.size() != 0) {
    316         nsecs_t now = systemTime(SYSTEM_TIME_MONOTONIC);
    317         const MessageEnvelope& messageEnvelope = mMessageEnvelopes.itemAt(0);
    318         if (messageEnvelope.uptime <= now) {
    319             // Remove the envelope from the list.
    320             // We keep a strong reference to the handler until the call to handleMessage
    321             // finishes.  Then we drop it so that the handler can be deleted *before*
    322             // we reacquire our lock.
    323             { // obtain handler
    324                 sp<MessageHandler> handler = messageEnvelope.handler;
    325                 Message message = messageEnvelope.message;
    326                 mMessageEnvelopes.removeAt(0);
    327                 mSendingMessage = true;
    328                 mLock.unlock();
    329 
    330 #if DEBUG_POLL_AND_WAKE || DEBUG_CALLBACKS
    331                 ALOGD("%p ~ pollOnce - sending message: handler=%p, what=%d",
    332                         this, handler.get(), message.what);
    333 #endif
    334                 handler->handleMessage(message);
    335             } // release handler
    336 
    337             mLock.lock();
    338             mSendingMessage = false;
    339             result = POLL_CALLBACK;
    340         } else {
    341             // The last message left at the head of the queue determines the next wakeup time.
    342             mNextMessageUptime = messageEnvelope.uptime;
    343             break;
    344         }
    345     }
    346 
    347     // Release lock.
    348     mLock.unlock();
    349 
    350     // Invoke all response callbacks.
    351     for (size_t i = 0; i < mResponses.size(); i++) {
    352         Response& response = mResponses.editItemAt(i);
    353         if (response.request.ident == POLL_CALLBACK) {
    354             int fd = response.request.fd;
    355             int events = response.events;
    356             void* data = response.request.data;
    357 #if DEBUG_POLL_AND_WAKE || DEBUG_CALLBACKS
    358             ALOGD("%p ~ pollOnce - invoking fd event callback %p: fd=%d, events=0x%x, data=%p",
    359                     this, response.request.callback.get(), fd, events, data);
    360 #endif
    361             // Invoke the callback.  Note that the file descriptor may be closed by
    362             // the callback (and potentially even reused) before the function returns so
    363             // we need to be a little careful when removing the file descriptor afterwards.
    364             int callbackResult = response.request.callback->handleEvent(fd, events, data);
    365             if (callbackResult == 0) {
    366                 removeFd(fd, response.request.seq);
    367             }
    368 
    369             // Clear the callback reference in the response structure promptly because we
    370             // will not clear the response vector itself until the next poll.
    371             response.request.callback.clear();
    372             result = POLL_CALLBACK;
    373         }
    374     }
    375     return result;
    376 }
    377 
    378 int Looper::pollAll(int timeoutMillis, int* outFd, int* outEvents, void** outData) {
    379     if (timeoutMillis <= 0) {
    380         int result;
    381         do {
    382             result = pollOnce(timeoutMillis, outFd, outEvents, outData);
    383         } while (result == POLL_CALLBACK);
    384         return result;
    385     } else {
    386         nsecs_t endTime = systemTime(SYSTEM_TIME_MONOTONIC)
    387                 + milliseconds_to_nanoseconds(timeoutMillis);
    388 
    389         for (;;) {
    390             int result = pollOnce(timeoutMillis, outFd, outEvents, outData);
    391             if (result != POLL_CALLBACK) {
    392                 return result;
    393             }
    394 
    395             nsecs_t now = systemTime(SYSTEM_TIME_MONOTONIC);
    396             timeoutMillis = toMillisecondTimeoutDelay(now, endTime);
    397             if (timeoutMillis == 0) {
    398                 return POLL_TIMEOUT;
    399             }
    400         }
    401     }
    402 }
    403 
    404 void Looper::wake() {
    405 #if DEBUG_POLL_AND_WAKE
    406     ALOGD("%p ~ wake", this);
    407 #endif
    408 
    409     uint64_t inc = 1;
    410     ssize_t nWrite = TEMP_FAILURE_RETRY(write(mWakeEventFd, &inc, sizeof(uint64_t)));
    411     if (nWrite != sizeof(uint64_t)) {
    412         if (errno != EAGAIN) {
    413             ALOGW("Could not write wake signal, errno=%d", errno);
    414         }
    415     }
    416 }
    417 
    418 void Looper::awoken() {
    419 #if DEBUG_POLL_AND_WAKE
    420     ALOGD("%p ~ awoken", this);
    421 #endif
    422 
    423     uint64_t counter;
    424     TEMP_FAILURE_RETRY(read(mWakeEventFd, &counter, sizeof(uint64_t)));
    425 }
    426 
    427 void Looper::pushResponse(int events, const Request& request) {
    428     Response response;
    429     response.events = events;
    430     response.request = request;
    431     mResponses.push(response);
    432 }
    433 
    434 int Looper::addFd(int fd, int ident, int events, Looper_callbackFunc callback, void* data) {
    435     return addFd(fd, ident, events, callback ? new SimpleLooperCallback(callback) : NULL, data);
    436 }
    437 
    438 int Looper::addFd(int fd, int ident, int events, const sp<LooperCallback>& callback, void* data) {
    439 #if DEBUG_CALLBACKS
    440     ALOGD("%p ~ addFd - fd=%d, ident=%d, events=0x%x, callback=%p, data=%p", this, fd, ident,
    441             events, callback.get(), data);
    442 #endif
    443 
    444     if (!callback.get()) {
    445         if (! mAllowNonCallbacks) {
    446             ALOGE("Invalid attempt to set NULL callback but not allowed for this looper.");
    447             return -1;
    448         }
    449 
    450         if (ident < 0) {
    451             ALOGE("Invalid attempt to set NULL callback with ident < 0.");
    452             return -1;
    453         }
    454     } else {
    455         ident = POLL_CALLBACK;
    456     }
    457 
    458     { // acquire lock
    459         AutoMutex _l(mLock);
    460 
    461         Request request;
    462         request.fd = fd;
    463         request.ident = ident;
    464         request.events = events;
    465         request.seq = mNextRequestSeq++;
    466         request.callback = callback;
    467         request.data = data;
    468         if (mNextRequestSeq == -1) mNextRequestSeq = 0; // reserve sequence number -1
    469 
    470         struct epoll_event eventItem;
    471         request.initEventItem(&eventItem);
    472 
    473         ssize_t requestIndex = mRequests.indexOfKey(fd);
    474         if (requestIndex < 0) {
    475             int epollResult = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, fd, & eventItem);
    476             if (epollResult < 0) {
    477                 ALOGE("Error adding epoll events for fd %d, errno=%d", fd, errno);
    478                 return -1;
    479             }
    480             mRequests.add(fd, request);
    481         } else {
    482             int epollResult = epoll_ctl(mEpollFd, EPOLL_CTL_MOD, fd, & eventItem);
    483             if (epollResult < 0) {
    484                 if (errno == ENOENT) {
    485                     // Tolerate ENOENT because it means that an older file descriptor was
    486                     // closed before its callback was unregistered and meanwhile a new
    487                     // file descriptor with the same number has been created and is now
    488                     // being registered for the first time.  This error may occur naturally
    489                     // when a callback has the side-effect of closing the file descriptor
    490                     // before returning and unregistering itself.  Callback sequence number
    491                     // checks further ensure that the race is benign.
    492                     //
    493                     // Unfortunately due to kernel limitations we need to rebuild the epoll
    494                     // set from scratch because it may contain an old file handle that we are
    495                     // now unable to remove since its file descriptor is no longer valid.
    496                     // No such problem would have occurred if we were using the poll system
    497                     // call instead, but that approach carries others disadvantages.
    498 #if DEBUG_CALLBACKS
    499                     ALOGD("%p ~ addFd - EPOLL_CTL_MOD failed due to file descriptor "
    500                             "being recycled, falling back on EPOLL_CTL_ADD, errno=%d",
    501                             this, errno);
    502 #endif
    503                     epollResult = epoll_ctl(mEpollFd, EPOLL_CTL_ADD, fd, & eventItem);
    504                     if (epollResult < 0) {
    505                         ALOGE("Error modifying or adding epoll events for fd %d, errno=%d",
    506                                 fd, errno);
    507                         return -1;
    508                     }
    509                     scheduleEpollRebuildLocked();
    510                 } else {
    511                     ALOGE("Error modifying epoll events for fd %d, errno=%d", fd, errno);
    512                     return -1;
    513                 }
    514             }
    515             mRequests.replaceValueAt(requestIndex, request);
    516         }
    517     } // release lock
    518     return 1;
    519 }
    520 
    521 int Looper::removeFd(int fd) {
    522     return removeFd(fd, -1);
    523 }
    524 
    525 int Looper::removeFd(int fd, int seq) {
    526 #if DEBUG_CALLBACKS
    527     ALOGD("%p ~ removeFd - fd=%d, seq=%d", this, fd, seq);
    528 #endif
    529 
    530     { // acquire lock
    531         AutoMutex _l(mLock);
    532         ssize_t requestIndex = mRequests.indexOfKey(fd);
    533         if (requestIndex < 0) {
    534             return 0;
    535         }
    536 
    537         // Check the sequence number if one was given.
    538         if (seq != -1 && mRequests.valueAt(requestIndex).seq != seq) {
    539 #if DEBUG_CALLBACKS
    540             ALOGD("%p ~ removeFd - sequence number mismatch, oldSeq=%d",
    541                     this, mRequests.valueAt(requestIndex).seq);
    542 #endif
    543             return 0;
    544         }
    545 
    546         // Always remove the FD from the request map even if an error occurs while
    547         // updating the epoll set so that we avoid accidentally leaking callbacks.
    548         mRequests.removeItemsAt(requestIndex);
    549 
    550         int epollResult = epoll_ctl(mEpollFd, EPOLL_CTL_DEL, fd, NULL);
    551         if (epollResult < 0) {
    552             if (seq != -1 && (errno == EBADF || errno == ENOENT)) {
    553                 // Tolerate EBADF or ENOENT when the sequence number is known because it
    554                 // means that the file descriptor was closed before its callback was
    555                 // unregistered.  This error may occur naturally when a callback has the
    556                 // side-effect of closing the file descriptor before returning and
    557                 // unregistering itself.
    558                 //
    559                 // Unfortunately due to kernel limitations we need to rebuild the epoll
    560                 // set from scratch because it may contain an old file handle that we are
    561                 // now unable to remove since its file descriptor is no longer valid.
    562                 // No such problem would have occurred if we were using the poll system
    563                 // call instead, but that approach carries others disadvantages.
    564 #if DEBUG_CALLBACKS
    565                 ALOGD("%p ~ removeFd - EPOLL_CTL_DEL failed due to file descriptor "
    566                         "being closed, errno=%d", this, errno);
    567 #endif
    568                 scheduleEpollRebuildLocked();
    569             } else {
    570                 // Some other error occurred.  This is really weird because it means
    571                 // our list of callbacks got out of sync with the epoll set somehow.
    572                 // We defensively rebuild the epoll set to avoid getting spurious
    573                 // notifications with nowhere to go.
    574                 ALOGE("Error removing epoll events for fd %d, errno=%d", fd, errno);
    575                 scheduleEpollRebuildLocked();
    576                 return -1;
    577             }
    578         }
    579     } // release lock
    580     return 1;
    581 }
    582 
    583 void Looper::sendMessage(const sp<MessageHandler>& handler, const Message& message) {
    584     nsecs_t now = systemTime(SYSTEM_TIME_MONOTONIC);
    585     sendMessageAtTime(now, handler, message);
    586 }
    587 
    588 void Looper::sendMessageDelayed(nsecs_t uptimeDelay, const sp<MessageHandler>& handler,
    589         const Message& message) {
    590     nsecs_t now = systemTime(SYSTEM_TIME_MONOTONIC);
    591     sendMessageAtTime(now + uptimeDelay, handler, message);
    592 }
    593 
    594 void Looper::sendMessageAtTime(nsecs_t uptime, const sp<MessageHandler>& handler,
    595         const Message& message) {
    596 #if DEBUG_CALLBACKS
    597     ALOGD("%p ~ sendMessageAtTime - uptime=%" PRId64 ", handler=%p, what=%d",
    598             this, uptime, handler.get(), message.what);
    599 #endif
    600 
    601     size_t i = 0;
    602     { // acquire lock
    603         AutoMutex _l(mLock);
    604 
    605         size_t messageCount = mMessageEnvelopes.size();
    606         while (i < messageCount && uptime >= mMessageEnvelopes.itemAt(i).uptime) {
    607             i += 1;
    608         }
    609 
    610         MessageEnvelope messageEnvelope(uptime, handler, message);
    611         mMessageEnvelopes.insertAt(messageEnvelope, i, 1);
    612 
    613         // Optimization: If the Looper is currently sending a message, then we can skip
    614         // the call to wake() because the next thing the Looper will do after processing
    615         // messages is to decide when the next wakeup time should be.  In fact, it does
    616         // not even matter whether this code is running on the Looper thread.
    617         if (mSendingMessage) {
    618             return;
    619         }
    620     } // release lock
    621 
    622     // Wake the poll loop only when we enqueue a new message at the head.
    623     if (i == 0) {
    624         wake();
    625     }
    626 }
    627 
    628 void Looper::removeMessages(const sp<MessageHandler>& handler) {
    629 #if DEBUG_CALLBACKS
    630     ALOGD("%p ~ removeMessages - handler=%p", this, handler.get());
    631 #endif
    632 
    633     { // acquire lock
    634         AutoMutex _l(mLock);
    635 
    636         for (size_t i = mMessageEnvelopes.size(); i != 0; ) {
    637             const MessageEnvelope& messageEnvelope = mMessageEnvelopes.itemAt(--i);
    638             if (messageEnvelope.handler == handler) {
    639                 mMessageEnvelopes.removeAt(i);
    640             }
    641         }
    642     } // release lock
    643 }
    644 
    645 void Looper::removeMessages(const sp<MessageHandler>& handler, int what) {
    646 #if DEBUG_CALLBACKS
    647     ALOGD("%p ~ removeMessages - handler=%p, what=%d", this, handler.get(), what);
    648 #endif
    649 
    650     { // acquire lock
    651         AutoMutex _l(mLock);
    652 
    653         for (size_t i = mMessageEnvelopes.size(); i != 0; ) {
    654             const MessageEnvelope& messageEnvelope = mMessageEnvelopes.itemAt(--i);
    655             if (messageEnvelope.handler == handler
    656                     && messageEnvelope.message.what == what) {
    657                 mMessageEnvelopes.removeAt(i);
    658             }
    659         }
    660     } // release lock
    661 }
    662 
    663 bool Looper::isPolling() const {
    664     return mPolling;
    665 }
    666 
    667 void Looper::Request::initEventItem(struct epoll_event* eventItem) const {
    668     int epollEvents = 0;
    669     if (events & EVENT_INPUT) epollEvents |= EPOLLIN;
    670     if (events & EVENT_OUTPUT) epollEvents |= EPOLLOUT;
    671 
    672     memset(eventItem, 0, sizeof(epoll_event)); // zero out unused members of data field union
    673     eventItem->events = epollEvents;
    674     eventItem->data.fd = fd;
    675 }
    676 
    677 } // namespace android
    678