本站消息

站长简介/公众号

  出租广告位,需要合作请联系站长

+关注
已关注

分类  

暂无分类

标签  

暂无标签

日期归档  

暂无数据

android treble项目&&HIDL学习总结

发布于2021-09-04 19:04     阅读(771)     评论(0)     点赞(27)     收藏(2)


概念介绍

Treble项目—HIDL产生背景,独立升级framework需求

Android O(8.0) 重新设计了 Android 操作系统框架,在一个名为Treble的项目中,以便让制造商能够以更低的成本更轻松、更快速地将设备更新到新版 Android 系统。在这种新架构中,HAL 接口定义语言HIDL指定了 HAL 和其用户之间的接口,让用户能够替换 android framework,而无需重新编译 HAL。
在这里插入图片描述

HIDL概念—HAL 接口定义语言,目标framework和HAL解耦

HIDL: HAL 接口定义语言HAL interface definition language。在 Android 8.0 中被全面使用,用于在可以独立编译的代码库之间进行通信的系统,定义Android Framework与Android HAL实现之间的接口。把framework和hal隔离,目的是使 Android 可以在不重新编译 HAL 的情况下对 Framework 进行 OTA 升级(OTA:Over The Air,一种远程无线升级技术,在线升级系统)。
在这里插入图片描述
HIDL与AIDL比较类似,底层也是基于binder机制。但是也有稍微不一样的地方。为了支持HIDL,Android 对BInder做了一定程度的修改,/dev/hwbinder。

HIDL的两种模式—Passthrough直通 / Binderized绑定

为了将以往设备的 Android 版本更新到 Android O,开发者需要将传统的 HAL 封装到新的 HIDL 接口中,这个接口为 HAL 提供了 Binder 模式以及 Passthrough 模式。
(1)Passthrough直通模式:对原先HAL的包装,老版本HAL的兼容,最终的binder service 跟binder client都是活在同一个进程当中,仅对 C++ 客户端与实现适用。
(2)Binderized绑定模式:Binder化的HAL,HAL都被写成了binder service,Android framework是binder client,两者再不同的上下文。
推出时即搭载了 Android 8.0 或后续版本的设备都必须只支持绑定式 HAL。如下图:
在这里插入图片描述

HIDL设计分析

HAL模块与package软件包(包含.hal文件)

每个HAL模块设计一个接口软件包package,可以具有子级,如 package.subpackage。已发布的 HIDL 软件包的根目录为 hardware/interfaces 或 vendor/vendorName。软件包名称在根目录下形成一个或多个子目录;定义同一个软件包的所有文件都位于同一目录下。
在这里插入图片描述软件包目扩展名为 .hal 的文件。每个文件均必须包含一个指定文件所属的软件包和版本的 package 语句。types.hal 文件(如果存在)并不定义接口,而是定义软件包中每个接口可以访问的数据类型。

.hal文件 语法简介

https://source.android.google.cn/devices/architecture/hidl/code-style
HIDL 语言与 C 语言类似。

注释:/** */ 表示文档注释(只用于类型、方法、字段和枚举值声明);/* */ 表示多行注释;// 表示注释一直持续到行尾;
[empty] 表示该字词可能为空。
? 跟在文本或字词后,表示它是可选的。
... 表示包含零个或多个项、使用指定的分隔符号分隔的序列。HIDL 中不含可变参数。
逗号用于分隔序列元素。
分号用于终止各个元素,包括最后的元素。
大写字母是非终止符。
italics 是一个令牌系列,如 integer 或 identifier(标准 C 解析规则)。
constexpr 是 C 样式的常量表达式(例如 1 + 11L << 3)。
import_name 是软件包或接口名称,按 HIDL 版本控制中所述的方式加以限定。
小写 words 是文本令牌。

.hal文件 (hidl-gen工具)编译转换.h/.cpp文件

hidl-gen 编译器会将 .hal 文件编译成一组 .h 和 .cpp 文件。 这些自动生成的文件可用来构建客户端/服务器实现链接到的共享库。用于构建此共享库的 Android.bp 文件由 hardware/interfaces/update-makefiles.sh 脚本自动生成。
在这里插入图片描述
IFoo.h :描述 C++ 类中的纯 IFoo 接口;它包含 IFoo.hal 文件中的 IFoo 接口中所定义的方法和类型,类的命名空间包含软件包名称和版本号,客户端和服务器都包含此标头:客户端用它来调用方法,服务器用它来实现这些方法。
IHwFoo.h :其中包含用于对接口中使用的数据类型进行序列化的函数的声明。开发者不得直接包含其标头(它不包含任何类)。
BpFoo.h : 从 IFoo 继承的类,可描述接口的 HwBinder 代理(客户端)实现。开发者不得直接引用此类。
BnFoo.h: 保存对 IFoo 实现的引用的类,可描述接口的 HwBinder 服务器端实现。开发者不得直接引用此类。
FooAll.cpp :包含 HwBinder 客户端和 HwBinder 服务器端的实现的类。当客户端调用接口方法时,代理会自动从客户端封送参数,并将事务发送到绑定内核驱动程序,该内核驱动程序会将事务传送到另一端的服务器端实现。

HIDL设计举例—hwc composer的分析

hwc composer是android里面对叠加器的加速,相关概念参考:https://blog.csdn.net/runafterhit/article/details/118884165
代码:http://androidxref.com/9.0.0_r3/xref/hardware/interfaces/graphics/composer/2.2/

composer相关源码分析

/hardware/interfaces/graphics/composer/2.2/
IComposer.hal:定义了composer模块的hal接口。

package android.hardware.graphics.composer@2.2;; // 指定文件所属的软件包和版本
import @2.1::IComposer; // 导入2.1的类
interface IComposer extends @2.1::IComposer {
	// 完全继承2.1包定义的IComposer
}
// 2.1包定义的IComposer 如下:
interface IComposer {
	getCapabilities() generates (vec<Capability> capabilities); // 获取能力级别
	dumpDebugInfo() generates (string debugInfo); // 打印debug信息
	createClient() generates (Error error, IComposerClient client); // 创建clenit实例
}

IComposerClient.hal:定义了composer的client的hal接口:

package android.hardware.graphics.composer@2.1; // 指定文件所属的软件包和版本
interface IComposerClient extends @2.2::IComposerClient {
	// 继承2.1包定义的IComposerClient ,同时专门新增了2.2相关功能接口,部分如下:
	getReadbackBufferFence(Display display) generates (Error error,handle acquireFence); // 获取buf的fence
}
// 2.1包定义的IComposerClient 如下:
interface IComposerClient {
	// 重点相关函数如下:
	registerCallback(IComposerCallback callback); // 回调注册接口
	createVirtualDisplay(/* 省略*/); // 创建虚拟display通道
 	createLayer(Display display, uint32_t bufferSlotCount) generates (Error error,Layer layer);	// 创建layer
 	destroyLayer(Display display, Layer layer) generates (Error error); // 销毁layer
 	setVsyncEnabled(Display display, Vsync enabled) generates (Error error); // 使能通道vsync
 	setInputCommandQueue(fmq_sync<uint32_t> descriptor) generates (Error error);// 设置输入命令到queue
 	executeCommands(/* 省略*/); // 直行命令queue中命令
 	// 还有各种设置属性接口
}

IComposerCallback.hal:定义client注册的回调类型,定义在2.1包中

package android.hardware.graphics.composer@2.1;
interface IComposerCallback {
	onHotplug(Display display, Connection connected); // display通路的拔插 回调
	oneway onRefresh(Display display); // display的刷新回调,强制刷新
	oneway onVsync(Display display, int64_t timestamp); // display的vsync信号回调
}

composer相关编译文件分析

在/hardware/interfaces/graphics/composer/目录下mm编译,会生成:
1、android.hardware.graphics.composer@2.2-service :service的可执行文件,生成在vendor/bin/hw/,见2.2/default/Android.mk中编译规则,service 服务的作用就是向 hwservicemanager 注册 HAL。
2、android.hardware.graphics.composer@2.2-service. rc : 启动配置脚本,直接从copy到vendor/etc/init。
3、android.hardware.graphics.composer@2.*. so:见composer/2.2/default/Android.mk,service编译时链接的共享库,在service进程加载时会链接进去。

composer启动流程分析

1、开机init进程会读取vendor/etc/init下的xxx_service. rc初始脚本文件,执行vendor/bin/hw/xx_service可执行文件,从而启动service进程:

// 脚本内容:
service vendor.hwcomposer-2-2 /vendor/bin/hw/android.hardware.graphics.composer@2.2-service
    class hal animation
    user system
    group graphics drmrpc
    capabilities SYS_NICE
    onrestart restart surfaceflinger

进程状态:

1|HWRVL:/vendor/etc/init $ ps -A | grep composer
system         610     1 2248748   2824 0                   0 S android.hardware.graphics.composer@2.2-service

2、进程启动后,servie执行main函数,建立Binder IPC 通信
/hardware/interfaces/graphics/composer/2.2/default/service.cpp,HIDL 框架为了支持供应商 HAL 进程,提供了 libbinder 用户空间库用于操作 Binder 设备节点(hwbinder & vndbinder)。然后调用HwcLoader::load()进行hwc模块加载

int main() {
    // the conventional HAL might start binder services
    android::ProcessState::initWithDriver("/dev/vndbinder");
    android::ProcessState::self()->setThreadPoolMaxThreadCount(4);
    android::ProcessState::self()->startThreadPool();
    // same as SF main thread
    struct sched_param param = {0};
    param.sched_priority = 2;
    if (sched_setscheduler(0, SCHED_FIFO | SCHED_RESET_ON_FORK, &param) != 0) {
        ALOGE("Couldn't set SCHED_FIFO: %d", errno);
    }
    android::hardware::configureRpcThreadpool(4, true /* will join */);
    android::sp<IComposer> composer = HwcLoader::load();
    if (composer == nullptr) {
        return 1;
    }
    if (composer->registerAsService() != android::NO_ERROR) {
        ALOGE("failed to register service");
        return 1;
    }
    return 1;
}

3、HWC模块load,这里最终调用到createComposer,其中主要实现调用hal::Composer::create(std::move(hal)) 来调用到ComposerHal 类中的
composer/2.2/utils/passthrough/include/composer-passthrough/2.2/HwcLoader.h

class HwcLoader : public V2_1::passthrough::HwcLoader {
   public:
    static IComposer* load() {
        const hw_module_t* module = loadModule();
        if (!module) {
            return nullptr;
        }
        auto hal = createHalWithAdapter(module);
        if (!hal) {
            return nullptr;
        }
        return createComposer(std::move(hal)).release();
    }
    /* 省略 */
    static std::unique_ptr<IComposer> createComposer(std::unique_ptr<hal::ComposerHal> hal) {
        return hal::Composer::create(std::move(hal));
    }
}

新增基于HIDL的HAL模块(待更新)

设计思路分析(待更新)

参考

官方文档:
https://source.android.google.cn/devices/architecture/hidl
https://source.android.google.cn/devices/architecture/hidl/code-style
HIDL概述:https://blog.csdn.net/u013357557/article/details/84561457
AndroidO Treble架构下Hal进程启动及HIDL服务注册过程:https://blog.csdn.net/yangwen123/article/details/79854267
https://blog.csdn.net/qq_19923217/article/details/88398660
https://blog.csdn.net/qq_19923217/article/details/89173162
https://blog.csdn.net/kuang_tian_you/article/details/86599869

原文链接:https://blog.csdn.net/runafterhit/article/details/119044112



所属网站分类: 技术文章 > 博客

作者:狗子你变了

链接:http://www.phpheidong.com/blog/article/140378/2caf793a322d0b0fc28f/

来源:php黑洞网

任何形式的转载都请注明出处,如有侵权 一经发现 必将追究其法律责任

27 0
收藏该文
已收藏

评论内容:(最多支持255个字符)