解析鸿蒙兼容运行安卓软件原理
应之前有些家友兄弟萌的愿望,我今天给大家讲一下有关于纯血鸿蒙( NEXT )之前的兼容安卓版本的混血鸿蒙(2.0-4.0)阶段是"基于安卓"还是兼容安卓的问题以及具体原理的问题,也是一个困扰大家多年且一直具有争议的问题。首先,第一个就是有关于 NEXT 之前的鸿蒙到底是如某些所谓"程序员"所云是"基于安卓"还是兼容安卓的问题,我这里首先引用一下当年 Openharmony 共建会上华为消费者 BG ,鸿蒙开源与开发者运营总监欧建深的解释:
OpenHarmony :
.开放原子开源基金会( OpenAtom Foundation )旗下开源项目,定位是一个面向全场景的开源分布式操作系统;
.项目包含了分布式操作系统所需的完整能力,包括内核层、系统服务层、应用框架层;
·华为及众多贡献者,在社区内直接贡献;
.欢迎社会各界力量参与一起贡献。
HarmonyOS :
.华为通过开源引入 OpenHarmony 开源项目,结合自研闭源应用和闭源 HMS 能力,构建华为自研产品的完整解决方案。
因此,通过欧建深的话我们可以清楚的知道,官方早就对 OpenHarmony 与 HarmonyOS 之间的关系作出了结论,即﹣--﹣鸿蒙是以 OpenHarmony 为基础,结合华为闭源 HMS 能力与其他自研闭源应用与技术而开发的商业发行版系统,也就是说,同安卓与 AOSP 之间的关系是类似的。
那么到这儿,肯定会有某些群体着急,问出诸如:"有很多人真正的"大佬"都已经给"实锤"了,到处都是安卓痕迹""都能无缝跑安卓软件了,底层一看就是"基于安卓"的,一定就是套壳"之类的话,相比之家其他的家友萌肯定都已经听的耳朵起茧了,那么,第二个问题便呼之欲出,鸿蒙兼容安卓的原理具体是什么样的呢?在这里呢,为了让大家更好的区分理解,我这里会分为两个部分来进行讲解,一个部分是2.0时代,另外一个部分是3.0-4.0时代。(1.0由于仅仅只是把鸿蒙微内核移植到了 TEE 部分,并未像 NEXT 一样将鸿蒙微内核拓展到 REE 部分,以及仅仅只移植了鸿蒙的核心能力分布式软总线技术到智慧屏系统中做为鸿蒙微内核安全性以及鸿蒙分布式软总线能力的技术验证,并没有上手机平板等其他智能设备上,因此不做赘述)
那么首先,我先来讲解鸿蒙2.0的兼容技术原理,在此之前,我先把官方开发人员对于鸿蒙兼容安卓原理(封面图)的文字进行复述:
1.复用开源项目 Linux Kernel 、 Nodejs 、 Gn 、 Ninja 、 OpenSSL 、 JerryScript 、 AOSP 等组件;
2.启动框架在合适的时机启动 Mygote 、 Foundation 进程;
3.在 Foundation 进程内启动系统关键服务 SAMgr 、 DMS 、 BMS 等;
4.各类业务 SAs 选择合适的时机通过 SA 框架启动;5.OpenHarmony应用运行时由 Mygote 孵化进程,提供 Maple 运行时环境。
第一条,我觉得之家的家友萌的实力,这些都是大路边上的常识了,我就不多赘述了。直接从第二条开始。
首先,我们要来了解下什么是 Mygote 和 Foundation , Mygote 这个最早是出现在2019年上半年随着华为p30系列手机发布后带来的方舟编译器而来,准备重新实现一个Java的AOT编译器。其实 Mygote 是对标安卓的 Zygote 而来,在讲述返方舟的 Mygote 之前,需要简单说一下安卓的 Zygote 是个啥,方便更好的理解鸿蒙中对应安卓的 Myogte 。
家友萌应该都知道, Android 系统中各种服务大多都是有背后的系统进程来进行支撑,而 fork 系统服务进程的就是 Zygote ,它的 fork 流程如下图所示
1.创建虚拟机实例
2.启动System Server
3.接收ActivityManagerService请求,创建app进程。
那么为什么安卓要设计Zygote这么个“东东”呢?其实最主要的目的就是减少内存开销,降低系统对硬件性能的消耗(cow技术),因此,鸿蒙的Mygote也和安卓Zygote一样,皆为其对象系统服务进程的的父进程,也都是由Linux内核启动的用户级进程init创建的,而init进程则是所有在Linux内核上构建系统的所有用户态进程的父进程,当然也是鸿蒙Linux内核版本系统中的父进程,其他进程的后续部署都是作为它的子进程而存在的,而init一般拉起后紧接着都会拉起Native daemon进程,由于daemon进程在拉起后会常驻后台进入死循环,因此又合称为“守护进程”。而那三个在鸿蒙中安卓兼容部分的启动就是由早期Java版本的方舟Maple runtime里面的Mygote进程fork而不是Zygote,(当然现阶段华为鸿蒙中也存在标准安卓的Zygote,用于未使用方舟编译器静态化的Java程序提供原始环境,只不过都是作为鸿蒙整体系统栈中“方舟多语言运行时子系统”模块之一存在其中,这也就为什么鸿蒙还能安装运行未经过方舟鸿蒙化的软件程序例如GMS全家桶的原因)
而Foundation又是什么呢,在鸿蒙整体技术栈里,对Foundation的定义,其能力对应安卓中System Server概念,为了更好的了解鸿蒙的Foundation,我们还是需要说一下与之对应的安卓System Server是个啥吧。
家友萌肯定知道,在安卓Framework中,大体可划分为客户端,服务端,内核端(内核端大多是Linux驱动部分)
而鸿蒙的Foundation其作用和安卓Framework不管是在功能还是在实现原理都和是类似的,但是却又和安卓不同,而是直接把对应的服务层框架层的系统服务直接打包进了Foundation进程内,这部分的设计从整体来看我认为应该是借鉴了苹果的Core Foundation的设计,但同时提供了与苹果不同的一些组件,比如华为自研的soft bus部分等。对于Foundation定义,官方在共建会说的很清楚——“Foundation是一个特殊的SA服务进程(System Ability),提供了用户程序管理框架及基础服务;由该进程负责应用的生命周期管理”。也就是说,在鸿蒙的Foundation进程中,包含了所有的鸿蒙系统上层实现所需的服务线程。那么安卓的System Server由虚拟机中的Zygote来fork,那鸿蒙的Foundation由谁fork呢,其实孵化Foundation的并不是方舟Maple的Mygote,而是底层启动子系统模块中的appspawn孵化,这个我们后面细讲(上面我们说的由方舟Mygote所fork出的鸿蒙程序其实是在EMUI时代后已经被方舟鸿蒙化整个系统框架组件的System Server,也就是兼容安卓的部分,至于什么是方舟鸿蒙化,这个我们也放在后面说)。
然后第三条,这里呢,DMS和BMS就先不说了,因为都只是进程中的面向不同task对象的基础服务线程,重点说一下 SAMgr,SAMgr(System Ability Manager),系统能力管理者,它的作用就是负责管理SA并向Client提供相关接口,Client如果想要根据用户的需求加载相应的SA,就必须通过SAMgr来注册一个ID,通过注册后的SA,SAMgr才会给Server一个Proxy,然后才能在Client构建相应服务所需的环境,才可以和SA通信。
而下图则为鸿蒙init进程树中SAMgr的启动顺序(从左往右)
然后我们到了第五条,第五条是官方在共建会上解析鸿蒙兼容原理的最后一条,也是我个人认为是解析兼容安卓生态原理的重中之重的部分了,之前我们上文提到了Mygote,对于Mygote,上面我们其实谈到了一部分,他是对应安卓的Zygote存在的,那么它的作用也是和Zygote一样的,其中作用之一便是创建System Server(方舟鸿蒙化的System Server),而Mygote用来fork鸿蒙中Java编写的hap软件所需的对应进程环境(在鸿蒙中,JS等语言编写的软件是由appspawn进程fork提供Foundation环境)。其实当年HDC2019华为首次发布鸿蒙1.0之前的EMUI9.1版本系统上华为就把Mygote加入进去了,就已经开始安卓系统鸿蒙化了(也就是很多花粉们说的“掏空安卓”),并已经对系统System Server部分进行鸿蒙化,构建起了相应配套环境。如下图所示:
—————————分割线——————————
以上则是鸿蒙2.0时代官方对于鸿蒙兼容安卓生态原理的阐述,然后根据官方的总结又做了一次详细的解析。
然而,由于美国进一步对华为的制裁,导致华为在鸿蒙3.0之后不得不转变开发方向以进一步规避制裁风险,也因此在鸿蒙3.0之后的版本,其兼容安卓的原理与2.0又有了许多的不同之处。关于3.0及其之后版本的兼容安卓原理,我的总结可以归纳为以下几点:
1.华为放弃以Java为生态发展主推的语言,转而以ArkTS(原名eTS),JS为生态发展主推的语言
2.华为的方舟编译器放弃以华为美研所(即FutureWei)所主导的方舟Maple Java编译器技术路线,转而才用方舟Maple JS/ArkTS编译器技术路线。
3.系统框架进一步进行解耦,出现了更明显的容器特征。
首先来说第一点,华为为什么会放弃以Java为生态发展主推的语言,是因为虽然Java有开源的SDK包(即Open JDK)华为可以使用,但是由于当时一方面美国升级制裁进一步限制华为,另外一方面是当时发生了一件事情,Oracle正在和Google因为Android上面的Java API是否侵权而打官司, 而判决直到2021年才以合理使用为由宣布Google胜诉。假如Oracle胜诉, 任何试图实现API互操作性但又没有API授权的使用都会被认为是侵权,因此,在当时被美国升级制裁情况下的华为高层自然担心使用Java语言作为自己主推生态发展的语言,必然会存在风险。
第二点,为什么放弃以华为美研所所主导的方舟Maple Java编译器技术路线。其实最主要的原因也是因为美国升级制裁。某些喷子们可能也很疑惑,怎么华为连自己家的海外研究所的代码都不能用了呢?一看就是在给华为洗白,啥事儿都往美国头上“甩锅”,从来不找自己身上的原因。大家要明白,美国的制裁可不是小儿科,咱们在国内看着华为啥问题都没大有,就觉得没啥影响,实际上一旦出了国,美国的制裁还是很强的,当时由于美国进一步升级制裁,要求所有包含一丁点儿美国技术的产品以及持有美国国籍的研发人员所开发的技术禁止为华为进行服务的,而华为的美研所就在美国的加州,里面是有很多持有美国国籍的研发人员的,因此就导致美研所和华为母公司完全中断联系, 只能以开源软件的方式向华为交付代码, 进而导致这个项目不了了之了。但是在代码托管平台Gitee上,还是能够在OpenArkcompiler项目里看到他存在的身影的,如下图所示。
而在/system/lib64下的OpenHarmony组件仍存在,如下图所示
本身就是基于安卓的部分开发的,虽然早在2.0时代进行了鸿蒙化,但是由于我之前说的那个原因导致华为并没有把方舟Mygote解耦出来,因此导致如果OHOS的进程实现如果想显示到GUI界面让用户看到,就必须要通过安卓的surface flinger来送显。)
libhilog.so, 日志库,很多库都在用这个库。
libmindspore-lite.huawei.mirror.so,被/system/lib64/libmindspore-lite.huawei.so使用, 是一个AI的运行时库,用于华为的NPU。
libsoftbus.so, 被/system/lib64/chipset-pub-sdk/libipc_core.z.so和/system/lib64/libdbinder.z.so使用, 是实现软总线的库。
libEGL.so和libGLESv3.so, 一看都带GL,就能联想到OpenGL,想必家友萌都不陌生,妥妥就是GPU驱动。
综上所述, 除了设备驱动之外, 鸿蒙3.0里的OpenHarmony不需要任何Android的组件(实际上其中麒麟机型设备驱动也是华为自己在EMUI时代自己开发的,只不过为了降低封包成本以及OTA稳定性,兼顾华为的高通机型用户,所以依旧复用了来自AOSP的驱动), 且结构与社区的OpenHarmony高度一致, JS/ArkTS应用的运行和渲染均在鸿蒙3.0里的OpenHarmony框架内完成, 仅有的送显由Android的surface flinger完成。
——————————分割线———————————
到这里,某些人肯定又要喷,鸿蒙3.0及其之后的版本,OpenHarmony都是以容器的形式存在的,离开OHOS照样可以开机,还说不是基于AOSP,不是套壳安卓呢。“程序员”说的就是对的,就是“真理”。
对于这种言论,个人认为真的是能让人笑掉大牙!!!
首先,基于Linux内核建构的操作系统都是可以逆转容器内外环境的,例如,将AOSP和部分依赖Android framework的驱动放入容器, 在外面运行OHOS的init(其实外面的init stage1阶段也是有部分OHOS核心进程的,这也就是某位“程序员”在禁用掉所有OHOS进程后依旧可以开机进桌面的原因,没有完全禁用完所有OHOS进程)、systemUI和launcher,完全就是一个OTA的事儿,而且一些手机上运行GNU/Linux系统的发行版也的确用过这种方式的,至于华为为什么要把OpenHarmony放在容器里而不是把AOSP放到容器里,完全是为了保证系统稳定性,降低封包和推送成本,因为客观的来说,鸿蒙生态相对于安卓生态来讲是远远不如的,用户使用的软件主力还是以安卓软件生态为主,因此保证对安卓软件兼容性是第一位的。其次,当下混血鸿蒙存在的目的就是为了保留华为存量手机用户,为纯血鸿蒙生态发展奠定用户数量基础的,所以混血鸿蒙仅仅只是一个过渡阶段,没有价值和必要再进行容器内外环境逆转了。(如果华为真的要是听了那些喷子们的话为了证明鸿蒙不是套壳安卓就放弃系统的稳定性,强行大规模OTA推送来逆转容器内外环境,恐怕就会和当年隔壁某厂的bug12一样大面积出现严重bug,到时候估计是神仙也救不回来没有网络舆论优势的华为了)。
再者,在混血鸿蒙最后一个版本4.2版本中,发现了一个更有意思的地方,高通机型的鸿蒙4.2和麒麟机型的4.2的OpenHarmony方式还有些不一样,高通机型的的4.2依旧和3.0一样是通过容器化,而麒麟机型的4.2则找不到容器进程,哎嘿,某些喷子阁下又应该作何解释呢?
能够看到这儿的家友必须要给自己点个赞,说实在的,码字码的我眼疼
。
当然了,如果能看到这儿的家友想必都会有一个问题,为什么华为一直迟迟不开源鸿蒙兼容安卓部分的工程代码实现,这个一开始我也比较纳闷,但是后来有一次参加华为线下HDD询问了他们的官方开发人员才知道,华为不开源一方面是因为华为在商业因素的考量,另一方面便是华为从EMUI9.1之后对安卓核心部分的鸿蒙化是花费了大量的人力物力的,且为了保证老HAP软件在鸿蒙上运行的稳定性,华为在其中加入了不少独有的闭源底层SDK以及可以直接调用AOSP框架的桥接层,因为这块在快速迭代变化中,每个版本都不同的不稳定接口,也没有开源的意义,况且说实在的,我估计华为不开源还有一个原因就是华为不想让这部分付之东流被某厂商给偷偷领先了。
如果家友萌想问我,当时为什么都发布鸿蒙了,但是却迟迟没有上手机的原因,我个人认为应该和当时华为高层对是否真正要与谷歌决裂的态度的摇摆不定造成的,毕竟当时华为还没有完成对EMUI的全部鸿蒙化,后来有次请客吃饭的时候听在华为工作的老同学说起,19年HDC大会后CBG紧接着就开始了百日“松湖会战”,当时任老爷子还让CNBG和EBG给提供各类技术支持,我寻思,华为应该就是从这个时候开始才下定决心,放弃幻想并与谷歌彻底决裂了,因此借着百日“松湖会战”加速了对安卓核心部分的鸿蒙化,也就是好多人说的“掏空安卓”,其实说的就是对安卓核心部分的鸿蒙化,为日后脱离安卓生态走向纯血鸿蒙铺路。虽然这期间由于美国进一步升级制裁导致华为不得不更改开发方向,进而导致了鸿蒙从发布起就没怎么有几个鸿蒙软件,耽误了好几年时间直到NEXT才终于稳定下来并宣布鸿蒙千帆起计划,进而厂商才敢开始跟进适配。但从今年华为HDC大会发布NEXT来看,不仅彻底摆脱AOSP生态,甚至是完成了鸿蒙微内核开发,并将其从原来只在TEE部分里承担安全任务拓展到REE部分,可以承担高负载任务调度,摆脱了Linux内核,做到了微内核比宏内核还要更加优秀的性能以及更高的安全性。并且近期又推送了一批NEXT给先锋用户体验。总而言之,大嘴没有只吹牛不干事儿,没有光说不练假把式,而是一步一步坚定推动鸿蒙的发展,到今年,成功完成了当年HDC2019大嘴在PPT上的演进图。在这点上,我是佩服大嘴的领导能力的,也是佩服华为的鸿蒙团队的整体实力的,绝对配得上那四个大字——遥遥领先!!!