在Android SurfaceFlinger服务启动过程源码分析中详细分析了SurfaceFlinger的整个启动过程,我们知道,在SurfaceFlinger线程执行过程中,循环调用waitForEvent()函数等待消息事件的到来

bool SurfaceFlinger::threadLoop()
{
    waitForEvent();
    return true;
}

而waitForEvent函数则是调用SurfaceFlinger中的消息队列的waitMessage()函数来等待消息事件

void SurfaceFlinger::waitForEvent() {
    mEventQueue.waitMessage();
}

通过跟踪代码发现,MessageQueue的waitMessage()函数则是调用Looper对象的pollOnce()函数来等待消息事件的

void MessageQueue::waitMessage() {
    do {
        IPCThreadState::self()->flushCommands();
        int32_t ret = mLooper->pollOnce(-1);
        switch (ret) {
            case ALOOPER_POLL_WAKE:
            case ALOOPER_POLL_CALLBACK:
                continue;
            case ALOOPER_POLL_ERROR:
                ALOGE("ALOOPER_POLL_ERROR");
            case ALOOPER_POLL_TIMEOUT:
                // timeout (should not happen)
                continue;
            default:
                // should not happen
                ALOGE("Looper::pollOnce() returned unknown status %d", ret);
                continue;
        }
    } while (true);
}

该函数无限循环执行,关于Looper的pollOnce()函数在Android应用程序消息循环源码分析有详细的分析过程。本文就针对SurfaceFlinger的消息队列MessageQueue展开讨论,分析SurfaceFlinger的消息队列创建过程。由于在Android SurfaceFlinger服务启动过程源码分析中对SurfaceFlinger的启动过程作了详细的介绍,这里只给出一些关键代码。

void SurfaceFlinger::onFirstRef()
{
	//消息队列初始化
    mEventQueue.init(this);
	//启动SurfaceFlinger线程
    run("SurfaceFlinger", PRIORITY_URGENT_DISPLAY);
    mReadyToRunBarrier.wait();
}

SurfaceFlinger消息循环过程

在SurfaceFlinger内部定义了类型为MessageQueue的消息队列。

void MessageQueue::init(const sp<SurfaceFlinger>& flinger)
{
    mFlinger = flinger;
    mLooper = new Looper(true);
    mHandler = new Handler(*this);
}

在初始化消息队列MessageQueue时,为该消息队列创建了一个Looper对象和一个Handler对象。SurfaceFlinger,MessageQueue,Looper,Handler对象之间的关系如下:

jq 监控select_jq 监控select

在SurfaceFlinger的消息队列MessageQueue的初始化函数中,该该消息队列创建了一个Handler对象,一个Looper对象,Android应用程序消息循环源码分析中分析了Handler,Looper类的相关知识,不过前面介绍的Handler对象是Java层的Handler对象,这里定义的Handler是C++层面的,Looper对象也是C++层的,不过在Android应用程序消息循环源码分析文中对Looper对象有详细的分析,这里就不在重复介绍,重点介绍C++层定义的Handler的实现过程及使用方法。既然SurfaceFlinger的消息队列拥有一个Looper对象,这就说明SurfaceFlinger线程是一个消息循环线程。那么SurfaceFlinger是如何处理消息的呢?

在前面的Android应用程序创建Surface过程源码分析中介绍了应用程序通过调用SurfaceFlinger为应用程序分配的Client对象的Binder远程代理对象的createSurface函数来创建一个Surface:

sp<ISurface> Client::createSurface(
        ISurfaceComposerClient::surface_data_t* params,
        const String8& name,
        DisplayID display, uint32_t w, uint32_t h, PixelFormat format,
        uint32_t flags)
{
    sp<MessageBase> msg = new MessageCreateSurface(mFlinger.get(),params, name, this, display, w, h, format, flags);
    mFlinger->postMessageSync(msg);
    return static_cast<MessageCreateSurface*>( msg.get() )->getResult();
}

函数首先将请求创建的Surface参数封装为MessageCreateSurface对象,然后调用SurfaceFlinger的postMessageSync函数往SurfaceFlinger的消息队列中发送一个同步消息,当消息处理完后,通过调用消息msg的getResult()函数来得到创建的Surface。

status_t SurfaceFlinger::postMessageSync(const sp<MessageBase>& msg,
        nsecs_t reltime, uint32_t flags) {
	//往消息队列中发送一个消息
    status_t res = mEventQueue.postMessage(msg, reltime);
	//消息发送成功后,当前线程等待消息处理
    if (res == NO_ERROR) {
        msg->wait();
    }
    return res;
}

其实这里发送的并不是消息对象,而是一个Handler对象,MessageCreateSurface的继承关系如下所示:

jq 监控select_MessageQueue_02

status_t MessageQueue::postMessage(const sp<MessageBase>& messageHandler, nsecs_t relTime)
{
    const Message dummyMessage;
	//将messageHandler对象和dummyMessage消息对象发送到消息循环Looper对象中
    if (relTime > 0) {
        mLooper->sendMessageDelayed(relTime, messageHandler, dummyMessage);
    } else {
        mLooper->sendMessage(messageHandler, dummyMessage);
    }
    return NO_ERROR;
}

关于消息循环Looper对象的消息发送函数sendMessage的调用流程在 Android应用程序消息循环源码分析已经有详细的分析。这里再次贴上关于消息插入代码:

void Looper::sendMessageAtTime(nsecs_t uptime, const sp<MessageHandler>& handler,
        const Message& message) {
    size_t i = 0;
    { // acquire lock
        AutoMutex _l(mLock);
		//获取消息队列中保存的消息个数
        size_t messageCount = mMessageEnvelopes.size();
		//按时间排序,查找当前消息应该插入的位置
        while (i < messageCount && uptime >= mMessageEnvelopes.itemAt(i).uptime) {
            i += 1;
        }
		//将Message消息及消息处理Handler封装为MessageEnvelope对象,并插入到消息队列mMessageEnvelopes中
        MessageEnvelope messageEnvelope(uptime, handler, message);
        mMessageEnvelopes.insertAt(messageEnvelope, i, 1);
        if (mSendingMessage) {
            return;
        }
    } // release lock
    //唤醒消息循环线程以及时处理消息
    if (i == 0) {
        wake();
    }
}

//所有C++层的消息都封装为MessageEnvelope类型的变量并保存到mMessageEnvelopes链表中
while (mMessageEnvelopes.size() != 0) {
	nsecs_t now = systemTime(SYSTEM_TIME_MONOTONIC);
	const MessageEnvelope& messageEnvelope = mMessageEnvelopes.itemAt(0);
	//处理当前时刻之前的所有消息
	if (messageEnvelope.uptime <= now) {
		{ 
			//取出处理该消息的Hanlder
			sp<MessageHandler> handler = messageEnvelope.handler;
			//取出该消息描述符
			Message message = messageEnvelope.message;
			//从mMessageEnvelopes链表中移除该消息
			mMessageEnvelopes.removeAt(0);
			//表示当前消息循环线程正在处理消息,处于唤醒状态,因此消息发送线程无需唤醒消息循环线程
			mSendingMessage = true;
			mLock.unlock();
			//调用该消息Handler对象的handleMessage函数来处理该消息
			handler->handleMessage(message);
		} // release handler
		mLock.lock();
		mSendingMessage = false;
		result = ALOOPER_POLL_CALLBACK;
	} else {
		// The last message left at the head of the queue determines the next wakeup time.
		mNextMessageUptime = messageEnvelope.uptime;
		break;
	}
}

消息处理过程就是调用该消息的Handler对象的handleMessage函数来完成,由于创建Surface时,往消息队列中发送的Handler对象类型为MessageCreateSurface,因此必定会调用该类的handleMessage函数来处理Surface创建消息。但该类并未实现

handleMessage函数,同时该类继承于MessageBase,由此可见其父类MessageBase必定实现了handleMessage函数:

void MessageBase::handleMessage(const Message&) {
    this->handler();
    barrier.open();
};

class MessageCreateSurface : public MessageBase {
	sp<ISurface> result;
	SurfaceFlinger* flinger;
	ISurfaceComposerClient::surface_data_t* params;
	Client* client;
	const String8& name;
	DisplayID display;
	uint32_t w, h;
	PixelFormat format;
	uint32_t flags;
public:
	MessageCreateSurface(SurfaceFlinger* flinger,
			ISurfaceComposerClient::surface_data_t* params,
			const String8& name, Client* client,
			DisplayID display, uint32_t w, uint32_t h, PixelFormat format,
			uint32_t flags)
		: flinger(flinger), params(params), client(client), name(name),
		  display(display), w(w), h(h), format(format), flags(flags)
	{
	}
	sp<ISurface> getResult() const { return result; }
	
	virtual bool handler() {
		result = flinger->createSurface(params, name, client,display, w, h, format, flags);
		return true;
	}
};

jq 监控select_EventThread_03

jq 监控select_MessageQueue_04

DisplayHardware对象创建过程

SurfaceFlinger线程启动后,首先会调用readyToRun()函数来完成一些线程运行前的准备工作

status_t SurfaceFlinger::readyToRun()
{
	// initialize the main display
	GraphicPlane& plane(graphicPlane(dpy));
	//创建DisplayHardware对象
	DisplayHardware* const hw = new DisplayHardware(this, dpy);
	plane.setDisplayHardware(hw);
	...
    //创建EventThread线程对象
    mEventThread = new EventThread(this);
    mEventQueue.setEventThread(mEventThread);
    hw.startSleepManagement();

    mReadyToRunBarrier.open();
    return NO_ERROR;
}

DisplayHardware::DisplayHardware(
        const sp<SurfaceFlinger>& flinger,
        uint32_t dpy)
    : DisplayHardwareBase(flinger, dpy),
      mFlinger(flinger), mFlags(0), mHwc(0)
{
    init(dpy);
}

DisplayHardwareBase::DisplayHardwareBase(const sp<SurfaceFlinger>& flinger,
        uint32_t displayIndex) 
{
    mScreenAcquired = true;
    mDisplayEventThread = new DisplayEventThread(flinger);
}

void DisplayHardware::init(uint32_t dpy)
{
    mNativeWindow = new FramebufferNativeWindow();
    framebuffer_device_t const * fbDev = mNativeWindow->getDevice();
    if (!fbDev) {
        ALOGE("Display subsystem failed to initialize. check logs. exiting...");
        exit(0);
    }
	...
    // initialize the H/W composer
    mHwc = new HWComposer(mFlinger, *this, mRefreshPeriod);
    if (mHwc->initCheck() == NO_ERROR) {
        mHwc->setFrameBuffer(mDisplay, mSurface);
    }
}

HWComposer::HWComposer(
        const sp<SurfaceFlinger>& flinger,
        EventHandler& handler,
        nsecs_t refreshPeriod)
    : mFlinger(flinger),
      mModule(0), mHwc(0), mList(0), mCapacity(0),
      mNumOVLayers(0), mNumFBLayers(0),
      mDpy(EGL_NO_DISPLAY), mSur(EGL_NO_SURFACE),
      mEventHandler(handler),
      mRefreshPeriod(refreshPeriod),
      mVSyncCount(0), mDebugForceFakeVSync(false)
{
    char value[PROPERTY_VALUE_MAX];
    property_get("debug.sf.no_hw_vsync", value, "0");
	//....
    if (needVSyncThread) {
        // we don't have VSYNC support, we need to fake it
        mVSyncThread = new VSyncThread(*this);
    }
}

1.DisplayHardware父类DisplayHardwareBase构造时创建了一个DisplayEventThread线程对象;

2.初始化DisplayHardware对象时创建了一个FramebufferNativeWindow对象;

3.初始化DisplayHardware对象时同时创建了一个HWComposer对象;

4.在HWComposer对象中创建了一个VSyncThread线程对象;

jq 监控select_jq 监控select_05

EventThread线程启动过程

EventThread对象构造过程:

EventThread::EventThread(const sp<SurfaceFlinger>& flinger)
    : mFlinger(flinger),
      mHw(flinger->graphicPlane(0).editDisplayHardware()),
      mLastVSyncTimestamp(0),
      mVSyncTimestamp(0),
      mUseSoftwareVSync(false),
      mDeliveredEvents(0),
      mDebugVsyncEnabled(false)
{
}

void EventThread::onFirstRef() {
    mHw.setVSyncHandler(this);
    run("EventThread", PRIORITY_URGENT_DISPLAY + PRIORITY_MORE_FAVORABLE);
}

void DisplayHardware::setVSyncHandler(const sp<VSyncHandler>& handler) {
    Mutex::Autolock _l(mLock);
    mVSyncHandler = handler;
}

DisplayHardware的成员变量mVSyncHandler的类型为VSyncHandler,而EventThread是VSyncHandler的子类

jq 监控select_jq 监控select_06

然后启动EventThread线程。到此SurfaceFlinger所需的几个重要对象就基本创建完成了,下图显示了SurfaceFlinger启动过程创建了重要对象:

jq 监控select_Socket_07

事件连接创建过程

SurfaceFlinger创建并启动完EventThread线程后,还会将该EventThread线程对象保存到SurfaceFlinger的消息队列mEventQueue中:

mEventQueue.setEventThread(mEventThread);

void MessageQueue::setEventThread(const sp<EventThread>& eventThread)
{
    mEventThread = eventThread;
    mEvents = eventThread->createEventConnection();
    mEventTube = mEvents->getDataChannel();
	//将socket接收端添加到looper中监听,并且设置了事件处理回调函数cb_eventReceiver
    mLooper->addFd(mEventTube->getFd(), 0, ALOOPER_EVENT_INPUT,MessageQueue::cb_eventReceiver, this);
}

jq 监控select_EventThread_08

EventThread类的createEventConnection()函数用于创建一个Connection对象:

sp<EventThread::Connection> EventThread::createEventConnection() const {
    return new Connection(const_cast<EventThread*>(this));
}

EventThread::Connection::Connection(
        const sp<EventThread>& eventThread)
    : count(-1), mEventThread(eventThread), mChannel(new BitTube())
{
}

BitTube::BitTube(): mSendFd(-1), mReceiveFd(-1)
{
    int sockets[2];
	//创建一对socket
    if (socketpair(AF_UNIX, SOCK_SEQPACKET, 0, sockets) == 0) {
        int size = SOCKET_BUFFER_SIZE;
        setsockopt(sockets[0], SOL_SOCKET, SO_SNDBUF, &size, sizeof(size));
        setsockopt(sockets[0], SOL_SOCKET, SO_RCVBUF, &size, sizeof(size));
        setsockopt(sockets[1], SOL_SOCKET, SO_SNDBUF, &size, sizeof(size));
        setsockopt(sockets[1], SOL_SOCKET, SO_RCVBUF, &size, sizeof(size));
        fcntl(sockets[0], F_SETFL, O_NONBLOCK);
        fcntl(sockets[1], F_SETFL, O_NONBLOCK);
        mReceiveFd = sockets[0];
        mSendFd = sockets[1];
    } else {
        mReceiveFd = -errno;
        ALOGE("BitTube: pipe creation failed (%s)", strerror(-mReceiveFd));
    }
}

jq 监控select_MessageQueue_09

Connection只是对进程间使用Socket通信的封装类。

jq 监控select_MessageQueue_10

EventThread类的createEventConnection()就是简单地创建一个Connection对象,在构造Connection对象时,创建了彼此相连的两个套接字,EventThread线程在接收到VSync信号后,将通过Connection中的套接字发送端向SurfaceFlinger的消息循环中发送一个事件,而Connection中的套接字接收端将注册到SurfaceFlinger的消息循环Looper中,以接收EventThread线程分发过来的VSync事件,上图形象地描述了EventThread线程和SurfaceFlinger的消息循环线程之间的通信过程。

事件连接Connection注册过程

由于Connection继承了RefBase类同时实现了onFirstRef()函数,因此在第一次强引用Connection对象时,onFirstRef()函数自动被调用:

void EventThread::Connection::onFirstRef() {
    // NOTE: mEventThread doesn't hold a strong reference on us
    mEventThread->registerDisplayEventConnection(this);
}

status_t EventThread::registerDisplayEventConnection(
        const sp<EventThread::Connection>& connection) {
    Mutex::Autolock _l(mLock);
	//将创建的Connection对象添加到EventThread的成员变量mDisplayEventConnections向量中
    mDisplayEventConnections.add(connection);
	//如果EventThread线程正处于睡眠等待,则唤醒EventThread线程
    mCondition.broadcast();
    return NO_ERROR;
}

事件连接Socket接收端注册过程

虽然此时创建了一对Socket用于EventThread线程和SurfaceFlinger的消息队列之间通信,但是消息队列MessageQueue并没有监听Socket的接收端描述符,因此即使EventThread线程通过Socket的发送端发送数据,消息队列MessageQueue仍然无法接收到EventThread线程发送的数据。这时需要将Socket的接收端文件描述符添加到MessageQueue的文件描述符监控池中:

mEventTube = mEvents->getDataChannel();
//将socket接收端添加到SurfaceFlinger的消息队列中监控
mLooper->addFd(mEventTube->getFd(), 0, ALOOPER_EVENT_INPUT,MessageQueue::cb_eventReceiver, this);

sp<BitTube> EventThread::Connection::getDataChannel() const {
    return mChannel;//mChannel(new BitTube())
}

int BitTube::getFd() const
{
    return mReceiveFd;
}

mLooper->addFd(mEventTube->getFd(), 0, ALOOPER_EVENT_INPUT,MessageQueue::cb_eventReceiver, this)就是将Socket接收端文件描述符添加到消息循环Looper对象中,并且监听该文件描述符下的ALOOPER_EVENT_INPUT事件,当该Socket接收端接收到消息事件后,调用回调函数MessageQueue::cb_eventReceiver来处理该事件。关于向消息循环中添加监控句柄过程在 Android应用程序消息循环源码分析中已经详细分析了,将Connection中的Socket接收端文件描述符注册到SurfaceFlinger的消息循环Looper中后,SurfaceFlinger的消息队列MessageQueue就可以接收到EventThread线程分发的事件消息了。