Android图形显示系统(GUI)是个非常复杂的一部分,涉及到Activity,WindowManagerService,Choreographer,VSync ,Jank,View,Surface,SurfaceFlinger
等。
大致如下:
本文仅涉及SurfaceFlinger相关分析。
下面带着这四个问题点去分析。
Android应用程序是如何与SurfaceFlinger服务建立连接的?
用来描述Android应用程序的UI元数据的SharedClient是如何创建的?
Android应用程序是如何请求SurfaceFlinger服务 创建 一个Surface的?
Android应用程序是如何请求SurfaceFlinger服务 渲染 一个Surface的?
1. Android应用程序是如何与SurfaceFlinger服务建立连接的?
Activity显示过程中,WindowManagerService 类addWindow 方法首先创建了 WindowState 对象,然后调用了其 attach() 方法。
// http://aosp.opersys.com/xref/android-12.0.0_r2/raw/frameworks/base/services/core/java/com/android/server/wm/WindowState.java
final Session mSession;
void attach() {
if (DEBUG) Slog.v(TAG, "Attaching " + this + " token=" + mToken);
mSession.windowAddedLocked();
}
然后调用了 windowAddedLocked()
。
// http://aosp.opersys.com/xref/android-12.0.0_r2/xref/frameworks/base/services/core/java/com/android/server/wm/Session.java#638
class Session extends IWindowSession.Stub implements IBinder.DeathRecipient {
final WindowManagerService mService;
SurfaceSession mSurfaceSession;
void windowAddedLocked() {
....
mSurfaceSession = new SurfaceSession();
mService.mSessions.add(this);
....
}
}
// http://aosp.opersys.com/xref/android-12.0.0_r2/xref/frameworks/base/services/core/java/com/android/server/wm/WindowManagerService.java
final ArraySet<Session> mSessions = new ArraySet<>();
这里重点如下:
1.创建了 SurfaceSession
2.将 Session 对象添加到 WindowManagerService 类 mSessions 中。
下面来看看SurfaceSession
。
// http://aosp.opersys.com/xref/android-12.0.0_r2/raw/frameworks/base/core/java/android/view/SurfaceSession.java
/**
* An instance of this class represents a connection to the surface
* flinger, from which you can create one or more Surface instances that will
* be composited to the screen.
* {@hide}
*/
public final class SurfaceSession {
// Note: This field is accessed by native code.
@UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
private long mNativeClient; // SurfaceComposerClient*
private static native long nativeCreate();
private static native void nativeDestroy(long ptr);
/** Create a new connection with the surface flinger. */
@UnsupportedAppUsage
public SurfaceSession() {
mNativeClient = nativeCreate();
}
/* no user serviceable parts here ... */
@Override
protected void finalize() throws Throwable {
try {
kill();
} finally {
super.finalize();
}
}
/**
* Remove the reference to the native Session object. The native object may still exist if
* there are other references to it, but it cannot be accessed from this Java object anymore.
*/
@UnsupportedAppUsage
public void kill() {
if (mNativeClient != 0) {
nativeDestroy(mNativeClient);
mNativeClient = 0;
}
}
}
这是一个hide标注的类,编译的时候会隐藏,说明不想让人调用。行数不多,所以都贴上来。
声明了private static native long nativeCreate();
,然后构造函数调用了nativeCreate
表示用到了JNI,实际的实现在C++里。
那么就要寻找Java对应的native函数。JNI中Java对应的Cpp的文件规则一般是
[包名]_[类名].cpp
,也就是说对应android_view_SurfaceSession.cpp
文件。
//http://aosp.opersys.com/xref/android-12.0.0_r2/xref/frameworks/base/core/jni/android_view_SurfaceSession.cpp
static jlong nativeCreate(JNIEnv* env, jclass clazz) {
SurfaceComposerClient* client = new SurfaceComposerClient();
client->incStrong((void*)nativeCreate);
return reinterpret_cast<jlong>(client);
}
incStrong
涉及到智能指针相关概念,这里可以理解为 增加对象的强引用计数的作用,也就是SurfaceComposerClient对象 强引用计数 +1。
创建了SurfaceComposerClient
,但SurfaceComposerClient
构造函数为空。
reinterpret_cast
用于任意类型的转换,允许将任意指针转换到其他指针类型。
指向client的指针 强转为指向 long 的指针(JNI中对应的名字是jlong),返回到 Java。
但是调用inStrong
会触发onFirstRef
方法。这个函数是要重点关注的。
// http://aosp.opersys.com/xref/android-12.0.0_r2/xref/frameworks/native/libs/gui/SurfaceComposerClient.cpp#1782
sp<SurfaceComposerClient> mClient;
SurfaceComposerClient::SurfaceComposerClient()
: mStatus(NO_INIT)
{
}
SurfaceComposerClient::SurfaceComposerClient(const sp<ISurfaceComposerClient>& client)
: mStatus(NO_ERROR), mClient(client)
{
}
void SurfaceComposerClient::onFirstRef() {
sp<ISurfaceComposer> sf(ComposerService::getComposerService());
if (sf != nullptr && mStatus == NO_INIT) {
sp<ISurfaceComposerClient> conn;
conn = sf->createConnection();
if (conn != nullptr) {
mClient = conn;
mStatus = NO_ERROR;
}
}
}
onFirstRef
中初始化了ISurfaceComposer
和ISurfaceComposerClient
。
要弄清楚这2个是什么。
// frameworks/native/libs/gui/SurfaceComposerClient.cpp
/*static*/ sp<ISurfaceComposer> ComposerService::getComposerService() {
ComposerService& instance = ComposerService::getInstance();
Mutex::Autolock _l(instance.mLock);
if (instance.mComposerService == nullptr) {
if (ComposerService::getInstance().connectLocked()) {
ALOGD("ComposerService reconnected");
}
}
return instance.mComposerService;
}
// frameworks/native/services/surfaceflinger/SurfaceFlinger.cpp
sp<ISurfaceComposerClient> SurfaceFlinger::createConnection() {
const sp<Client> client = new Client(this);
return client->initCheck() == NO_ERROR ? client : nullptr;
}
// frameworks/native/libs/gui/ISurfaceComposer.cpp
virtual sp<ISurfaceComposerClient> createConnection()
{
Parcel data, reply;
data.writeInterfaceToken(ISurfaceComposer::getInterfaceDescriptor());
remote()->transact(BnSurfaceComposer::CREATE_CONNECTION, data, &reply);
return interface_cast<ISurfaceComposerClient>(reply.readStrongBinder());
}
先分析getComposerService
,再看createConnection
。
1.getComposerService
调用ComposerService::getComposerService()
会走到connectLocked()
,然后调用
waitForService<ISurfaceComposer>(name)
,初始化instance.mComposerService
,而这个name
,connectLocked
中定义了const String16 name("SurfaceFlinger")
。
这里实际是通过ServiceManager
和SurfaceFlinger
这个String
,获取到了SurfaceFlinger服务。
// frameworks/native/include/private/gui/ComposerService.h
sp<ISurfaceComposer> mComposerService;
//frameworks/native/libs/gui/SurfaceComposerClient.cpp
ComposerService::ComposerService()
: Singleton<ComposerService>() {
Mutex::Autolock _l(mLock);
connectLocked();
}
bool ComposerService::connectLocked() {
const String16 name("SurfaceFlinger");
mComposerService = waitForService<ISurfaceComposer>(name);
if (mComposerService == nullptr) {
return false; // fatal error or permission problem
}
// Create the death listener.
.......
return true;
}
//frameworks/native/libs/fakeservicemanager/ServiceManager.cpp
sp<IBinder> ServiceManager::waitForService(const String16& name) {
return checkService(name);
}
// frameworks/native/libs/binder/IServiceManager.cpp
sp<IBinder> ServiceManagerShim::checkService(const String16& name) const
{
sp<IBinder> ret;
if (!mTheRealServiceManager->checkService(String8(name).c_str(), &ret).isOk()) {
return nullptr;
}
return ret;
}
// frameworks/native/cmds/servicemanager/ServiceManager.cpp
Status ServiceManager::checkService(const std::string& name, sp<IBinder>* outBinder) {
*outBinder = tryGetService(name, false);
// returns ok regardless of result for legacy reasons
return Status::ok();
}
sp<IBinder> ServiceManager::tryGetService(const std::string& name, bool startIfNotFound) {
auto ctx = mAccess->getCallingContext();
sp<IBinder> out;
Service* service = nullptr;
if (auto it = mNameToService.find(name); it != mNameToService.end()) {
service = &(it->second);
if (!service->allowIsolated) {
uid_t appid = multiuser_get_app_id(ctx.uid);
bool isIsolated = appid >= AID_ISOLATED_START && appid <= AID_ISOLATED_END;
if (isIsolated) {
return nullptr;
}
}
out = service->binder;
}
if (!mAccess->canFind(ctx, name)) {
return nullptr;
}
if (!out && startIfNotFound) {
tryStartService(name);
}
if (out) {
// Setting this guarantee each time we hand out a binder ensures that the client-checking
// loop knows about the event even if the client immediately drops the service
service->guaranteeClient = true;
}
return out;
}
binder通讯架构如下所示。
https://blog.csdn.net/codefly/article/details/17058607
http://gityuan.com/2015/11/21/binder-framework/
https://www.cnblogs.com/roger-yu/p/15714247.html
SurfaceFlinger作为典型的Binder系统服务,遵循Binder服务设计的一般原则:
Interface接口:ISurfaceComposer 、ISurfaceComposerClient
Bp客户端:BpSurfaceComposer、BpSurfaceComposerClient
Bn服务端:BnSurfaceComposer、BnSurfaceComposerClient
服务实现:SurfaceFlinger、Client
mComposerService
定义是ISurfaceComposer
,实际从ServiceManager
返回的是BpSurfaceComposer
。
mComposerService
代表了SurfaceFlinger服务的代理客户端。
2.sf->createConnection()
sf
代表的是SurfaceFlinger
服务。那么就应该调用 SurfaceFlinger.cpp中的SurfaceFlinger::createConnection()
。
// frameworks/native/services/surfaceflinger/SurfaceFlinger.cpp
sp<ISurfaceComposerClient> SurfaceFlinger::createConnection() {
const sp<Client> client = new Client(this);
return client->initCheck() == NO_ERROR ? client : nullptr;
}
关于怎么到SurfaceFlinger.cpp
的,因为remote()->transact(BnSurfaceComposer::CREATE_CONNECTION, data, &reply)
。
// frameworks/native/libs/gui/ISurfaceComposer.cpp
virtual sp<ISurfaceComposerClient> createConnection()
{
Parcel data, reply;
data.writeInterfaceToken(ISurfaceComposer::getInterfaceDescriptor());
remote()->transact(BnSurfaceComposer::CREATE_CONNECTION, data, &reply);
return interface_cast<ISurfaceComposerClient>(reply.readStrongBinder());
}
SurfaceFlinger
端通过onTransact
接口收到CREATE_CONNECTION
消息后,实际调用了父类BnSurfaceComposer::onTransact
接口进行动作分发,这里会再调到SurfaceFlinger
的createConnection
方法。
createConnection
这里以SurfaceFlinger
为参数,新建了Client
。Client
继承自BnSurfaceComposerClient
。explicit
关键字用于修饰只有一个参数的类构造函数。~
和= default
函数表示析构函数。
Client::Client(const sp<SurfaceFlinger>& flinger) : mFlinger(flinger)
相当于Client::Client(const sp<SurfaceFlinger>& flinger) {mFlinger= flinger;}
。
这种写法是类名::类名(形参表):内嵌对象1(形参表),内嵌对象2(形参表)... { 类的初始化 }
使用初始化列表比使用赋值语句效率高。C++中有很多有意思的写法。
//frameworks/native/services/surfaceflinger/Client.cpp
class Client : public BnSurfaceComposerClient
{
public:
explicit Client(const sp<SurfaceFlinger>& flinger);
~Client() = default;
status_t initCheck() const;
.....
// constant
sp<SurfaceFlinger> mFlinger;
.....
}
//http://aosp.opersys.com/xref/android-12.0.0_r2/xref/frameworks/native/services/surfaceflinger/Client.cpp#40
Client::Client(const sp<SurfaceFlinger>& flinger)
: mFlinger(flinger)
{
}
status_t Client::initCheck() const {
return NO_ERROR;
}
因此,conn
定义是ISurfaceComposerClient
,实际创建的对象是BnSurfaceComposerClient
。
回到我们一开始的问题,Android应用程序是如何与SurfaceFlinger服务建立连接的?
通过SurfaceComposerClient
类来与SurfaceFlinger
服务建立一个连接了。
从WindowState
到Client
流程是
WindowState.attach() ->Session ->SurfaceSession ->nativeCreate->onFirstRef->getComposerService(获取surfaceflinger 服务)和createConnection(以surfaceflinger 服务为参数new Client)
。
SurfaceSession
中的mNativeClient
,持有 surfaceflinger
服务的client,这样就联系起来了。
// frameworks/base/core/java/android/view/SurfaceSession.java
private long mNativeClient; // SurfaceComposerClient*
/** Create a new connection with the surface flinger. */
@UnsupportedAppUsage
public SurfaceSession() {
mNativeClient = nativeCreate();
}
参考链接:
Android应用程序与SurfaceFlinger服务的关系概述和学习计划
Android 源码 图形系统之 WindowState attach
Android图形系统(六)-app与SurfaceFlinger服务连接过程
Android智能指针
Android 12(S) 图像显示系统 - 应用建立和SurfaceFlinger的沟通桥梁(三)
SurfaceFlinger系列01--Android应用与SurfaceFlinger的连接过程
网友评论