徽州骆驼 · 2022年07月06日

软件定义汽车 (第七集) : 高性能计算单元架构

导读:

前一篇文章中介绍了传统ECU的特点及开发模式,在中央计算电子电气架构下,中央计算单元都会采用高性能的SOC来作为主运算单元,由于其资源的丰富性,其开发模式和开发的复杂度,相比与传统的ECU都大有不同,因此,对应的软件架构(逻辑,物理,运行,部署等架构视图)、软件工程中各个环节(设计、开发、测试、部署等过程)都不相同。本篇主要介绍中央计算单元的软件架构,阐述各个软件模块主要工作任务。

1. 高性能计算单元

中央计算单元,其实就是一台经过特殊设计的专用计算机,其中最核心的是主芯片,一般会采用一颗或多颗高性能的SOC。SOC是System on Chip的缩写,就是在单块芯片上集成多个微处理器、模拟IP核、数字IP核和存储器等部件,比如CPU、GPU、DSP、ISP、Codec、NPU、Modem等模块。

在传统PC时代,各个核心芯片都是以独立的方式存在,比如英特尔和AMD的CPU、NVIDIA的GPU等,到了移动互联网时代,由于体积功耗方面的要求,主芯片都会进行高度的集成,除了大家熟知的CPU和GPU,通常还包含了音频、多媒体、显示、安全、通信、AI计算等子单元。
image.png

soc.jpeg

这些单元,在一套总线系统的连接下,构成了一个系统。大家所熟知的各种手机SOC芯片,如苹果的A系列、高通的骁龙系列、华为的麒麟系列,或者各类的AI SOC芯片,车载领域的各种SOC芯片,都逃不出以上范式。

虽然都是同一范式,但是由于使用的场景不同,各个芯片的侧重点不太一样:

  • 娱乐系统芯片,其实和消费电子几乎一模一样,关注音频、视频、显示、图像等、Modem等。
  • 自动驾驶芯片,注重高性能计算,一般配备有强大的NPU、GPU、DSP等。
  • 网关芯片,主要特点是外设接口较多,有的也会集成swtich。

image.png

高性能计算单元.png

上一篇中,为大家介绍了传统ECU芯片的架构,其计算资源相对有限,结构也比较简单,一般NVM和SRAM都集成在了芯片内部,大小在KB级别,处理器一般采用Cortex-M内核。高性能的SOC其计算资源和外设都更加丰富,一般会集成多个Cortex-A内核,其存储单元采用外挂的形式,大小在GB级别。

一般的应用场景中,集成一个主芯片就能够满足计算资源的需求,但是自动驾驶对算力有着更高的要求,有时候 于安全的考虑,也需要同时集成多个主芯片,其结构一般如下图所示:

image.png

cc-architecture.png

多个芯片在需要在PCIe Switch的连接下共同组成一个计算单元,如果以后发展成可动态拓展的形式(类似于刀片机),该结构依然适用,以下是采用两个Xavier芯片组成的一个高性能计算单元的示意图:

image.png

xavier.png

2.  中央计算单元上的软件架构

高性能计算单元上是需要运行操作系统的,如果完全用裸机程序去控制,几乎无法完成。从下到上,依次可分为以下几个部分,硬件驱动层,操作系统内核,分布式中间件,并行计算中间件,应用及服务。

硬件驱动层(BSP)

在嵌入式软件开发当中,软件工程师经常要直接和硬件进行交互,但是在高性能计算单元上,由于有富操作系统的存在,这部分工作一般由BSP工程师完成。

BSP(Board Support Package)板级支持包,是介于硬件和操作系统中驱动层程序之间的一层,一般认为它属于操作系统一部分,主要是实现对操作系统的支持,为上层的驱动程序提供访问硬件设备寄存器的函数包,不同的操作系统对应于不同形式的BSP,尽管实现的功能一样,可是写法和接口定义是完全不同的,BSP的编程过程大多数是在某一个成型的BSP模板上进行修改,芯片厂商一般会基于其开发板,提供一个可运行的软件基线,开发厂商基于该基线进行修改。

BSP的调试工作是和硬件强相关的,目前普遍会选择由硬件Tier1做掉这部分工作,由于本身的技术壁垒不高,所以有余力的玩家选择自己做也完全不是什么问题。

操作系统内核

在软件定义汽车1-3合集中,我对操作系统的概念做过辨析,为了避免歧义,这里我直接称操作系统内核,很多玩家所谓的做自己的操作系统,其实都只是内核之上的中间件。这部分不是主机厂该做的事情,用QNX、Vxworks、Linux、FreeRTOS等,或者以后的鸿蒙微内核即可。虽然这种不直接面向C端用户的操作系统对应用生态的要求不高,但是对于开发者生态的要求还是挺高的。使用这些操作系统的时候,有几个因素至关重要:

  • POSIX兼容性
  • 工具链

POSIX是一个操作系统的接口标准,如果一个操作系统对于POSIX兼容性好,那么开源世界中的很多软件模块是可以复用的。举一个例子,cocos2dx 是一个开源的游戏引擎,支持windows、Linux、Mac等系统,不支持QNX系统,但是由于QNX系统良好的兼容了POSIX,我们只花了很少的功夫就把其移植到了QNX上,虽然cocos2dx依赖了好几十个开源的软件库,但调用的都是标准的POSIX接口,所以也都能非常方便的进行移植。有些网关开发中会使用FreeRTOS,其也有专门的拓展库来支持POSIX调用。

举一个反面的例子,Halide是一个专用的图像处理引擎,其构建是基于LLVM编译器框架的,由于QNX官方支持的编译器是基于GNU GCC的,我曾经尝试过要把Halide移植到QNX,但是由于编译器不支持,迁移过程就碰到了很大的困难。所以系统所支持的编译器框架,也决定了很多最新的开源项目是否能被使用。

传统主机厂,不喜欢开源软件,其中最重要的一个原因,是其技术实力太弱,出了问题自己无法解决,但是新的科技玩家,会更加的拥抱开源软件。

主机厂自己做软件,虽然不用去碰内核,但是必须有几个系统方面的高手,主要是应对系统的稳定性问题,这个对于安全性较高的控制器尤为重要,软件进度上的问题堆人力可以弥补,但涉及到架构、性能、稳定性、安全等,做这部分工作就不是靠堆人力能解决的。

分布式中间件

参考软件定义汽车1-3,所谓的分布式中间件,就是在实时的RTOS内核上,基于POSIX的API,构建的一个跨平台的操作系统中间件,为上层的应用提供良好的计算、通信的开发框架,其作用类似于Android的Framework,只不过主要是针对实时、高可靠性应用场景的。

这类Framework中间件,有三个核心要素:

  • Library(提供一系列基础库,封装特定功能)
  • Service (独立运行的基础服务节点,作为逻辑处理的后端)
  • SDK (为上层应用提供良好的API接口)

从功能上讲,这类Framework中间件,一般需要包含以下功能:

  • 包管理(应用管理):基于基础软件平台开发的上层应用,在编译之后会被打成一个应用程序包,在这个包中一般会有一个manifest文件,该文件声明该包的版本,依赖,所需权限,生命周期,启动选项等。当该应用安装到系统中的时候,包管理程序会解析该manifest文件,得到的元数据会保存到数据库当中,这些数据是后续该应用能够正常运行,正常升级的关键。
  • 运行管理:系统在启动阶段,各个应用程序需要按照预先定义的启动顺序被拉起来;在运行阶段,管理程序需要记录当前应用的状态,处理应用生命周期的各种事件。比如手机和PC程序都会有前台应用的概念,当打开、关闭、重启、切换等事件发生的时候,系统的运行管理程序都会发送一个消息给应用,让其做好相应的处理工作。不同的点在于,面向消费者的操作系统,都是可以让用户操作的,所以大部分的逻辑是与人机交互事件有关的,而面向车辆底层的系统,更多的是在后台处理相关的事件请求,其设计策略与逻辑完全不同。
  • 通信管理:运行在分布式系统上的各个应用程序,是需要进行数据交互的,这就需要一类IPC/RPC的框架来支撑;IPC是指本机间的进程通信,RPC是指跨机器的间的远程调用,在分布式系统当中这两种通信都会碰到。比如在linux中常用的dbus,Android中使用的binder,以及前面文章中提到的DDS与some/IP。作为一个基础软件平台,一般是不会把这些原始的通信方法暴露给上层应用的,Framework会有自己的API去屏蔽底层通信协议的差异,这在架构设计中很关键,决定了框架是否和某一通信中间件绑死。如果还在拿dds与someip的原始接口写程序,意味着根本就没有进行平台化设计。
  • 权限管理:安全在车上是一个更加重要的问题,一个用户和应用程序具有哪些权限,应该是被严格控制的。在应用程序的manifest当中,一般会声明该程序具有哪些权限,权限管理程序会根据包管理程序解析的元数据来严格控制应用程序的访问权限。一些高安全等级要求的访问权限,一般还会需要经过特别签名,以此来防止一些非法应用获得系统权限。在类unix系统当中,权限系统一般会根据UID和GID为基础进行设计,但是在车载环境中,此类权限系统也还不够,还需要进行更加严格的权限控制。
  • 升级管理:能够不断的进行软件升级是软件定义汽车的基础,传统的ECU,一般都会生成一个bin文件,是没有所谓的包管理程序的概念的,要升其实就是把整个分区给刷掉了。这种方式针对传统的ECU并没有什么问题,但是针对高性能计算单元,这种方式的效率就很低,刷KB级的数据和刷GB级的数据,完全不是一个概念。为了高效的进行迭代,平台升级和应用升级一定是需要分开。平台升级类似于手机的ROM升级,而应用升级类似于手机的APP升级,一个长周期,一个短周期。要实现这种升级方式,是需要一个良好设计的基础软件平台的,应用与系统必须彻底解耦,这对架构设计是非常大的挑战。很遗憾,国内目前没一家能够做到这个水平,大家都会拿车的复杂性说事,其实是因为设计上的短板造成的,国内的几个先驱公司都被这个事情所困扰。因为在前期发展的过程中,都只注重短期功能的实现,没有真正的在工程能力方面下功夫。
  • 其他的还有像诊断、日志、持久化、加密等功能性的模块,就不一一展开,后续可以针对每一部分的设计进行详细阐述。

这类中间件的平台,是一个基础的工具,各家之间没必要重复造轮子,行业是有一个adaptive autosar,但是目前还远远不够完善,特别是在并行计算方面。不只是在车载领域,整个中国的软件行业就没有一家像样的中间件公司,和一些投资机构的朋友也聊到了这个问题,我认为最大原因还是这类产品属于工程产品,客户都更愿意看到一个完整的解决方案,而不是给他提供一个中间件,之前快的节奏让大家都只愿意做来钱快的事情,这些慢活儿也没有成长的土壤。

但是在目前的政治环境之下,这种情况似乎迎来了一丝改变,一些贸易冲突,也让大家意识到了,老老实实打基础还是挺重要的。中国汽车行业最大的问题在于,这些玩家都觉得自己挺牛逼的,谁也不买谁的单,都想自己搞一套,但是在这个事情上,真心不是哪一个能独自搞定的。所以我还是建议,大家能够联合起来做点事情,哪怕是投点钱支持一些创业公司搞开源,也比自己搞要靠谱。就算是一家主机厂发起了一个开源项目,大概率其他的主机厂也不会用,必须以中立的身份来做,才能获得大家共同的认可。

服务及应用层

参考软件定义汽车1-3, 在一个标准的基础软硬件平台之上,各家主机厂可以构建自己的服务和应用体系,这也是各家能够形成差异化的地方。针对不同的应用场景(智驾、座舱、网关、车控等),以及各自差异化的硬件设备,抽象一套属于自己的服务体系,SOA只是实现目的的一种方式,大家可以根据自己的理解去拆解、分层、分类,然后形成一套自己的SDK体系,以支持产品业务的快速迭代。

在此基础上,我也期待有一天,能在各个车厂之间形成统一的接口定义的标准,那样一个应用就能够部署到所有车上,这其实是在从Tier1的角度看问题,Classic AutoSAR就是在这个愿景上产生的,对主机厂来说,只要自己所有车型能够统一,就是一个伟大的成就了。

3.  并行计算框架

随着自动驾驶与智能座舱的发展,大量的以视觉为主的传感器部署到了车上,产生的数据需要高算力的计算单元来处理,就需要一个并行计算的框架来支撑应用程序的开发与部署。原则上来讲,该框架应该属于上面介绍的分布式计算框架的一部分,主要是这部分内容与传统的应用框架不太一样,所以拿出来单独讲。

image.png

parallel processing.png

目前有各种各样的AI计算芯片,但总体上都是CPU+协处理器的基本构型;CPU可以是基于ARM的IP,协处理可以是GPU、NPU、DSP、FPGA等,这些异构的计算单元,都会有自己的指令集。CPU擅长于做逻辑处理,这些并行计算单元擅长于做高性能计算,汽车电子软件公众号之前有文章介绍这几种计算单元的差异,有兴趣的可以去了解。

工作原理

大部分SOC都会采用这种主+从的方式,比如NVIDIA采用是CPU+GPU,高通采用CPU+GPU+ NPU+DSP,TI也采用CPU+GPU+ NPU+DSP,赛灵思采用CPU+FPGA等。

开发人员写的程序,虽然都在一个工程当中,但是在编译阶段,通过芯片厂商提供的工具链,代码会被编译成为两个部分:运行在CPU上的,与运行在异构单元上的,芯片厂商会提供一个基础的通信框架,来处理这部分逻辑。

在程序运行阶段,这两部分程序都会被加载到内存当中,由于SOC的总线设计当中很容易做到内存共享,各个计算单元会各自读取运行的指令与参数,通过芯片厂商提供的RPC框架,主程序可以很方便与协处理器进行逻辑通信。

需要注意的是,高性能计算的并不仅是运行CNN网络,还有其他的很多计算任务需要用到并行计算,并且每种计算单元的程序开发模型都不太一样,如果每部分都需要开发人员自己去处理,开发过程会非常复杂。

比如NVIDIA提供CUDA库来支持GPU上的并行计算,在CUDA之上又构建了TensorRT来运行神经网络;高通提供的SNPE框架,能够支持任务自动调度到CPU、GPU、NPU、DSP之上。当前阶段,这些框架都是和芯片高度绑定的,目前还没有一个通用的框架来屏蔽所有的差异。

除了底层的运行框架不统一之外,上层的应用开发框架也没有一个统一标准。比如NVIDIA提供了DRIVE AV平台,用于支持使用自家芯片进行自动驾驶应用的开发;很多公司基于ROS开发原型系统;也有创业公司基于ROS2进行车规化改造;还有一些使用Adaptive AutoSAR进行开发,但这部分恰好是其短板。

这部分实现想统一的确有比较大的困难,因为与芯片架构强相关,现阶段AI芯片的种类五花八门,在硬件构型不统一的的状态下,只能先选择芯片,再决定技术架构。

图片

4. 结语

本篇从大的维度上介绍了高性能计算单元上软件架构的几个重要部分,每个一个部分其实都值得继续进行深入。硬件单元的不同,也会导致软件框架的设计出现一些特性差异,比如在一个双冗余的计算单元中,除了硬件的fallback设计,软件上如何进行fallback,可选方案有多种,也不是非此即彼的问题。

此类专业的问题,没人给出最佳实践,即使是特斯拉也是在不断的摸索当中,解决此类问题,模仿只是一种途径,正向的去思考,去设计,也是一种有效途径。软件定义汽车社区,慢慢已经积累了不少专家,后续将会开展一些技术研讨会,也欢迎各位提供问题与素材。

作者:Leo Huang SDV
来源:汽车电子与软件
微信公众号:  
 title=  

推荐阅读:

更多汽车电子干货请关注汽车电子与软件专栏。欢迎添加极术小姐姐微信(id:aijishu20)加入技术交流群,请备注研究方向。
推荐阅读
关注数
5618
内容数
334
汽车电子与软件行业的相关技术报道及解读。
目录
极术微信服务号
关注极术微信号
实时接收点赞提醒和评论通知
安谋科技学堂公众号
关注安谋科技学堂
实时获取安谋科技及 Arm 教学资源
安谋科技招聘公众号
关注安谋科技招聘
实时获取安谋科技中国职位信息