经过上一篇的概览, 我们对 Android 图形系统渲染流程有了一个大致的了解, 这篇开始做细节分析. 那么先来总结下 App 与 SurfaceFlinger 服务连接过程.
经过前面的 activity ,Windows ,view 的分析我们大致了解了 Activity 的显示过程. 其实 Surface 的创建过程与 Activity 的显示过程密不可分.
那么就从 Activity.makeVisible 开始捋下流程:
1 Activity.makeVisible getWindowManager() 并执行 addView.
2 经过 WindowManagerImpl 和 WindowManagerGlobal addView , 最终创建了 ViewRootImpl
3 ViewRootImpl 内部会 new Surface() , 它是一个 Parcelable 对象, 可在进程间传递, 但目前仅是一个空壳, 还未被赋值.
同时, 通过 WindowManagerGlobal.getWindowSession() 获取了 Session 实例, 准备好了与 WMS 通信, 并且 Session 内有个成员变量 SurfaceSession 值得关注, 它的初始化是在 Session 的 windowAddedLocked 方法, 先埋个伏笔.
4 根据流程我们知道, 最终 ViewRootImpl 会在走 setView, 在这个方法中开始了两个流程:
requestLayout() 开启了绘制流程.
- mWindowSession.addToDisplay(mWindow, mSeq, mWindowAttributes,
- getHostVisibility(), mDisplay.getDisplayId(),
- mAttachInfo.mContentInsets, mAttachInfo.mStableInsets,
mAttachInfo.mOutsets, mInputChannel); binder ipc 让 WMS 执行添加并显示 Windows 操作.
我们先来看看 mWindowSession.addToDisplay, 这个过程最终是在 WMS 执行 addWindow 方法:
- addWindow(...){
- ...
- // 创建 WindowState , WindowState 是系统层面对 Windows 管理的一个封装类, 与 Windows 一一对应的.
- WindowState win = new WindowState(...);
- ...
- // 别的都不看了, 重点关注 attach 方法
- win.attach();
- ...
- }
- //WindowState.java
- void attach() {
- mSession.windowAddedLocked();//mSession 是 Session
- }
我们之前埋过伏笔的, windowAddedLocked 创建了 SurfaceSession 对象, 并将当前 Session 添加到 WMS.mSessions 成员变量. SurfaceSession 的创建会调用 JNI, 在 JNI 调用 nativeCreate().
从这里开始要细说下了, 这是应用程序与 SurfaceFlinger 建立连接的关键点:
跟踪到 android_view_SurfaceSession.cpp 的 nativeCreate() 方法, 创建了 SurfaceComposerClient 对象, 并且将这个对象赋值给类型为 sp<SurfaceComposerClient > 的智能指针 mSession 时, 就会导致 SurfaceComposerClient 类的成员函数 onFirstRef 被调用:
- void SurfaceComposerClient::onFirstRef() {
- sp<ISurfaceComposer> sm(ComposerService::getComposerService());
- if (sm != 0) {
- sp<ISurfaceComposerClient> conn = sm->createConnection();
- if (conn != 0) {
- mClient = conn;
- mStatus = NO_ERROR;
- }
- }
- }
SurfaceComposerClient 类的成员函数 getComposerService 用来获得 SurfaceFlinger 服务的一个代理接口.
- sp<ISurfaceComposer> ComposerService::getComposerService() {
- return ComposerService::getInstance().mComposerService;
- }
ComposerService 类是单例模式, 当我们第一次调用它的静态函数 getInstance 的时候, 它就会在构造函数中获得 SurfaceFlinger 服务的一个代理接口, 并且保存在它的成员变量 mComposerService 中, 同时会通过这个代理接口的成员函数 getCblk 来获得一块匿名共享内存 mServerCblkMemory. 这块匿名共享内存是由 SurfaceFlinger 服务创建的, 用来描述系统显示屏的信息, 例如, 显示屏的个数, 大小, 方向, 密度等等信息.
- ComposerService::ComposerService()
- : Singleton<ComposerService>() {
- const String16 name("SurfaceFlinger");
- while (getService(name, &mComposerService) != NO_ERROR) {
- usleep(250000);
- }
- mServerCblkMemory = mComposerService->getCblk();
- mServerCblk = static_cast<surface_flinger_cblk_t volatile *>(
- mServerCblkMemory->getBase());
- }
这时候 sm 有值了, 在接着 onFirstRef() 往下执行:
- sp<ISurfaceComposerClient> conn = sm->createConnection();
- sp<ISurfaceComposerClient> SurfaceFlinger::createConnection()
- {
- sp<ISurfaceComposerClient> bclient;
- sp<Client> client(new Client(this));
- status_t err = client->initCheck();
- if (err == NO_ERROR) {
- bclient = client;
- }
- return bclient;
- }
是不是感觉特别绕, 下面来简单总结下:
首先 ComPoserService 作为 client 与 SurfaceFlinger server 进行 binder IPC , 获取到 SurfaceFlinger 创建的 Client 对象, 它相当于是 SurfaceFlinger 内部对应用程序客户端的封装对象, 而 Client 与 SurfaceComposerClient 又互为 binder ipc 的两端, SurfaceComposerClient 为 client 端, Client 为 server 端.
这样, 应用进程成功通过 SurfaceComposerClient 与 SurfaceFlinger 建立了连接.
下篇分析 App 请求 SurfaceFlinger 创建 Surface 过程.
参考:
来源: http://www.jianshu.com/p/6964157c2615