標籤:添加檔案 有關 一個 sel val framework ice tran his
SurfaceFlinger有著自己的訊息佇列MessageQueue,用來處理顯示相關的訊息,比如Vsync訊息。
相關檔案:
- frameworks/native/services/surfaceflinger/MessageQueue.h
- frameworks/native/services/surfaceflinger/MessageQueue.cpp
類MessageQueue和Handler定義在MessageQueue.h檔案中,代碼如下:
class MessageQueue { // 類Handler定義也在這裡 class Handler : public MessageHandler { enum { eventMaskInvalidate = 0x1, eventMaskRefresh = 0x2, eventMaskTransaction = 0x4 }; MessageQueue& mQueue; int32_t mEventMask; public: Handler(MessageQueue& queue) : mQueue(queue), mEventMask(0) { } virtual void handleMessage(const Message& message); void dispatchRefresh(); void dispatchInvalidate(); void dispatchTransaction(); }; friend class Handler; sp<SurfaceFlinger> mFlinger; sp<Looper> mLooper; sp<EventThread> mEventThread; sp<IDisplayEventConnection> mEvents; sp<BitTube> mEventTube; sp<Handler> mHandler; static int cb_eventReceiver(int fd, int events, void* data); int eventReceiver(int fd, int events); public: enum { INVALIDATE = 0, REFRESH = 1, TRANSACTION = 2 }; MessageQueue(); ~MessageQueue(); void init(const sp<SurfaceFlinger>& flinger); void setEventThread(const sp<EventThread>& events); void waitMessage(); status_t postMessage(const sp<MessageBase>& message, nsecs_t reltime=0); // sends INVALIDATE message at next VSYNC void invalidate(); // sends REFRESH message at next VSYNC void refresh(); // sends TRANSACTION message immediately void invalidateTransactionNow();};
- mLooper線程迴圈體,主要用於取訊息
- mHander訊息處理類
- mEventThread、mEvents、mEventTube主要與Vsync訊息的分發有關
SurfaceFlinger類中有一個MessageQueue類型的成員變數,定義如下:
// these are thread safe mutable MessageQueue mEventQueue;
- 因些在SurfaceFlinger被構造的時候就構造一個mEventQueue。
void SurfaceFlinger::onFirstRef(){ mEventQueue.init(this);}
- 調用MessageQueue的init函數進行初始化
void MessageQueue::init(const sp<SurfaceFlinger>& flinger){ mFlinger = flinger; mLooper = new Looper(true); mHandler = new Handler(*this); }
- 初始化mFlinger、mLooper、mHandler三個成員變數
void SurfaceFlinger::init() { ...... mSFEventThread = new EventThread(sfVsyncSrc); mEventQueue.setEventThread(mSFEventThread); ...... }
- 在SurfaceFlinger的init函數中調用MessageQueue的setEventThread函數
void MessageQueue::setEventThread(const sp<EventThread>& eventThread){ mEventThread = eventThread; mEvents = eventThread->createEventConnection(); mEventTube = mEvents->getDataChannel(); mLooper->addFd(mEventTube->getFd(), 0, Looper::EVENT_INPUT, MessageQueue::cb_eventReceiver, this);}
- 設定mEventThread、mEvents、mEventTube,並且添加檔案控制代碼到mLooper
訊息的監聽主要在SurfaceFlinger的run函數裡
void SurfaceFlinger::run() { do { waitForEvent(); } while (true);}
- 死迴圈一直監聽訊息
- 調用waitForEvent進行等待訊息事件
void SurfaceFlinger::waitForEvent() { mEventQueue.waitMessage();}
- 調用MessageQueue的waitMessage等待訊息
void MessageQueue::waitMessage() { do { IPCThreadState::self()->flushCommands(); int32_t ret = mLooper->pollOnce(-1); switch (ret) { case Looper::POLL_WAKE: case Looper::POLL_CALLBACK: continue; case Looper::POLL_ERROR: ALOGE("Looper::POLL_ERROR"); case Looper::POLL_TIMEOUT: // timeout (should not happen) continue; default: // should not happen ALOGE("Looper::pollOnce() returned unknown status %d", ret); continue; } } while (true);}
- waitMessage主要通過調用mLooper的pollOnce方法來監聽訊息
Android SurfaceFlinger服務(四) ----- 訊息機制MessageQueue