04 深入探究waitForService<ISurfaceComposer>

前面分析《构造surfaceComposerClient》里有这样一段代码

bool ComposerService::connectLocked() {
    const String16 name("SurfaceFlinger");
    mComposerService = waitForService<ISurfaceComposer>(name);
    if (mComposerService == nullptr) {
        return false; // fatal error or permission problem
    }
... ...
}

waitForService,本篇来深入看下其实现。

android12\frameworks\native\libs\binder\include\binder\IServiceManager.h
template<typename INTERFACE>
sp<INTERFACE> waitForService(const String16& name) {
    const sp<IServiceManager> sm = defaultServiceManager();
    return interface_cast<INTERFACE>(sm->waitForService(name));
}

android12\frameworks\native\libs\binder\include\binder\IInterface.h
template<typename INTERFACE>
inline sp<INTERFACE> interface_cast(const sp<IBinder>& obj)
{
    return INTERFACE::asInterface(obj);
}

看不出来,将模板类替换成ISurfaceComposer

sp<ISurfaceComposer> waitForService(const String16& name) {
    const sp<IServiceManager> sm = defaultServiceManager();
    return interface_cast<ISurfaceComposer>(sm->waitForService(name));
}

inline sp<ISurfaceComposer> interface_cast(const sp<IBinder>& obj)
{
    return ISurfaceComposer::asInterface(obj);
}

赶紧找一下ISurfaceComposer的asInterface的实现。

找了半天没找到,,,,又找了半天终于找到了,原来是用宏藏起来了

android12\frameworks\native\libs\gui\include\gui\ISurfaceComposer.h
class ISurfaceComposer: public IInterface {
public:
    DECLARE_META_INTERFACE(SurfaceComposer)
... ...
}

把宏展开之后是这个样子

#define DECLARE_META_INTERFACE(INTERFACE)                               \
public:                                                                 \
    static const ::android::String16 descriptor;                        \
    static ::android::sp<ISurfaceComposer> asInterface(                     \
            const ::android::sp<::android::IBinder>& obj);              \
    virtual const ::android::String16& getInterfaceDescriptor() const;  \
    ISurfaceComposer();                                                     \
    virtual ~ISurfaceComposer();                                            \
    static bool setDefaultImpl(std::unique_ptr<ISurfaceComposer> impl);     \
    static const std::unique_ptr<ISurfaceComposer>& getDefaultImpl();       \
private:                                                                \
    static std::unique_ptr<ISurfaceComposer> default_impl;                  \
public:                                                                 \

看起来这里只是声明,然后继续找。。。。。。

终于在android12\frameworks\native\libs\gui\ISurfaceComposer.cpp中发现了

IMPLEMENT_META_INTERFACE(SurfaceComposer, "android.ui.ISurfaceComposer");

展开宏之后可以看到如下实现:

    ::android::sp<ISurfaceComposer> ISurfaceComposer::asInterface(              \
            const ::android::sp<::android::IBinder>& obj)               \
    {                                                                   \
        ::android::sp<ISurfaceComposer> intr;                               \
        if (obj != nullptr) {                                           \
            intr = ::android::sp<ISurfaceComposer>::cast(                   \
                obj->queryLocalInterface(ISurfaceComposer::descriptor));    \
            if (intr == nullptr) {                                      \
                intr = ::android::sp<BpSurfaceComposer>::make(obj);         \
            }                                                           \
        }                                                               \
        return intr;                                                    \
    }                                                                   \

哦豁,重点,,原来使用interface_cast会使用binder指针创建一个BpSurfaceComposer。

来看下BpSurfaceComposer

BpSurfaceComposer实现了很多接口,来和BnSurfaceComposer交互。以createConnection为例

android12\frameworks\native\libs\gui\ISurfaceComposer.cpp
class BpSurfaceComposer : public BpInterface<ISurfaceComposer>
{
public:
    explicit BpSurfaceComposer(const sp<IBinder>& impl)
        : BpInterface<ISurfaceComposer>(impl)
    {
    }

    virtual ~BpSurfaceComposer();

    virtual sp<ISurfaceComposerClient> createConnection()
    {
        Parcel data, reply;
        data.writeInterfaceToken(ISurfaceComposer::getInterfaceDescriptor());
        remote()->transact(BnSurfaceComposer::CREATE_CONNECTION, data, &reply);
        return interface_cast<ISurfaceComposerClient>(reply.readStrongBinder());
    }
    ... ...
}

《构造surfaceComposerClient》里conn = sf->createConnection();

没有详细介绍,在这里介绍一下:

conn = sf->createConnection();这里实际会调用到BpSurfaceComposer::createConnection();

通过binder,发送远程调用BnSurfaceComposer::CREATE_CONNECTION;

BnSurfaceComposer::onTransact中会收到CREATE_CONNECTION;并执行createConnection()。

status_t BnSurfaceComposer::onTransact(
    uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
{
    switch(code) {
        case CREATE_CONNECTION: {
            CHECK_INTERFACE(ISurfaceComposer, data, reply);
            sp<IBinder> b = IInterface::asBinder(createConnection());
            reply->writeStrongBinder(b);
            return NO_ERROR;
        }
}

因为SurfaceFlinger继承BnSurfaceComposer,所以这里调用的是SurfaceFlinger::createConnection()。

class SurfaceFlinger : public BnSurfaceComposer,
                       public PriorityDumper,
                       private IBinder::DeathRecipient,
                       private HWC2::ComposerCallback,
                       private ISchedulerCallback {
... ...
}

将创建的Client进行转换并通过Binder返回。

回过头来在看sp<ISurfaceComposerClient> createConnection()

    virtual sp<ISurfaceComposerClient> createConnection()
    {
        Parcel data, reply;
        data.writeInterfaceToken(ISurfaceComposer::getInterfaceDescriptor());
        remote()->transact(BnSurfaceComposer::CREATE_CONNECTION, data, &reply);
        return interface_cast<ISurfaceComposerClient>(reply.readStrongBinder());
    }

用返回的binder指针,创建BpSurfaceComposerClient,这个过程和本次分析的一致。

总结:

本文梳理了一下waitForService的内部机制,和Bpxxx/Bnxxx的调用过程,这样做应该是为了代码重用。

有了BpSurfaceComposer就可以远程调用SurfaceFlinger的各种接口。

如下图

创造不易,欢迎点赞收藏。 

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Revit是一种功能强大的建筑信息建模(BIM)软件,提供多种高效调试和深入探究内部世界的方法。 首先,为了高效调试Revit模型,我们可以使用Revit的内置调试工具。通过查看模型元素的属性、构件等信息,我们可以快速定位问题并进行修复。在Revit中,我们还可以使用选择集和过滤器等功能来选择和管理模型中的元素,帮助我们更好地理解和调试模型。 其次,深入探究Revit的内部世界可以通过多种途径实现。首先,我们可以仔细阅读Revit的帮助文档和教程,了解软件的各种功能和工具。同时,Revit还提供了丰富的插件和API开发工具,可以根据自己的需求进行功能扩展和定制开发,从而深入了解和探索Revit的内部结构。 此外,参加相关的培训课程和研讨会也是深入研究Revit内部世界的好方法。这些课程通常由经验丰富的Revit专家主讲,可以分享实际案例和应用经验,助于我们更好地理解Revit的设计思想和内部机制。 最后,通过实践和项目经验,我们也可以逐步深入探究Revit的内部世界。在实际项目中,我们可以不断尝试和应用Revit的各种功能和工具,了解它们的特点和应用场景,不断完善和提升自己的Revit技能。 总而言之,通过高效调试和深入探究Revit内部世界,我们可以更好地理解和应用这一建筑信息建模软件,提高工作效率,实现更优质的建筑设计和施工。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值