当前位置: 首页 > 后端技术 > Java

当Java遇上机密计算,开启另一段奇幻之旅!

时间:2023-04-02 00:27:50 Java

简介:王少军:如何为Java业务提供机密计算保护?在信息世界中,数据存在三种状态:存储状态、传输状态和计算状态。存储在数据库或磁盘中的数据属于存储状态,在网络中传输的数据属于传输状态,正在计算和处理的数据属于计算状态。我们需要从数据的三种状态来进行系统安全防护,才能保证真正的数据安全。对于存储和传输数据的安全问题,我们可以采用广泛使用的数据加密技术进行有效保护。计算数据安全保护仍然是一个新的前沿领域。基于硬件的机密计算技术(TEE),通过提供一个可信的执行环境,在这个环境中运行的代码和数据将在硬件层面得到保护,包括内核和Hypervisor在内的任何软件都无权窥探环境中的数据信息,从而实现对计算状态数据的保护。全球主流芯片厂商纷纷推出自己的保密计算解决方案,如IntelSGX、ArmTrustZone等。TrustZone主要应用于终端领域,而SGX技术则可以应用于服务器领域。SGX技术可以提供极高级别的机密计算保护,但是由于SGX技术在内存资源和编程模型上的限制,无法有效支撑Java生态的机密计算业务,不得不说是一个遗憾.随着阿里云神龙架构第七代ECS实例的发布,其搭载的新一代IntelSGX2技术为我们构建基于Java生态的机密计算服务提供了条件。Java机密计算Demo演示下面,我们通过一个具体的例子来演示如何为Java业务提供机密计算保护。本实例基于第三代神龙架构第七代ECS实例构建,在SGX2提供的机密计算可信执行环境中运行JavaSpringBoot网络服务。准备申请一个支持SGX2的神龙架构第七代ECS实例,EPC内存规格不要太小24G;下载LibOS:Occlum容器镜像occlum/occlum:0.20.0-ubuntu18.04;下载JDK:AlibabaDragonwell11(Alpine),阿里巴巴发布的基于Alpine平台的Dragonwell11镜像版本;下载SpringBoot源码:Demo,展示了一个基于SpringBoot框架的简单网络服务;将SpringBootDemo源码下载到本地后,进入初始目录编译打包。目录下会生成spring-boot-0.0.1-SNAPSHOT.jar,我们先在正常环境下运行jar包验证其功能:mvncleanpackagejava-jarspring-boot-0.0.1-SNAPSHOT.jar到搭建SGX执行环境先登录ECS实例;在ECS环境下,通过docker命令进入Occlum容器;dockerrun-it--rm--privileged--networkhost\-v`pwd`:`pwd`\-v/dev/sgx_enclave:/dev/sgx/enclave\-v/dev/sgx_provision:/dev/sgx/provision\-v/var/run/aesmd:/var/run/aesmd\occlum/occlum:0.20.0-ubuntu18.04在Occlum容器中,创建一个enclave实体。实例包含一个json配置文件和一个image镜像文件夹;mkdirocclum_instancecdocclum_instanceoccluminit修改Occlum.json文件,包括堆大小、入口点、env环境变量;resource_limits.user_space_size="1680MB"resource_limits.kernel_space_heap_size="64MB"resource_limits.max_num_of_threads=64process.default_heap_size="256MB"process.default_mmap_size="1400MB"entry_points=["/usr/lib/jvm/java-11-alibaba-dragonwell/jre/bin"]env.default=["LD_LIBRARY_PATH=/usr/lib/jvm/java-11-alibaba-\dragonwell/jre/lib/server:/usr/lib/jvm/java-11-alibaba-dragonwell/jre/lib:/usr/lib/jvm/java-11-\alibaba-dragonwell/jre/../lib"]运行Java需要更大的内存空间。entry_points选项表示JDK在OcclumLibOS中的放置路径。JDK的路径必须是xx/xx/jre/bin方式,需要设置LD_LIBRARY_PATH环境变量。由于目前的OcclumLibOS不支持exec系统调用,JDK路径需要满足一定的条件,才能避免JVM虚拟机启动时的exec系统调用。进入image文件夹,在该目录下创建usr/lib/jvm/java-11-alibaba-dragonwell文件目录,放置Dragonwell11AlpineJDK。注意JDK压缩文件解压后的文件夹名称要重命名为jre,以保证与.json配置文件一致;创建usr/lib/spring文件目录,用于放置之前准备好的SpringBootspring-boot-0.0.1-SNAPSHOT.jar文件。请注意,图像文件目录将是SGXLibOS运行后的根目录。将Occlum容器环境中的libz.so.1文件复制到image/lib;cp/usr/local/occlum/x86_64-linux-musl/lib/libz.so.1image/lib构建机密镜像image;occlum构建启动SGX机密计算服务;occlum运行/usr/lib/jvm/java-11-alibaba-dragonwell/jre/bin/java-Xmx512m-XX:-\UseCompressedOops-XX:MaxMetaspaceSize=64m-Dos.name=Linux-jar/usr/lib/spring/spring-\boot-0.0.1-SNAPSHOT.jarSpringBoot启动后,使用命令curllocalhost:8080请求SpringBoot服务,得到“GreetingsfromSpringBoot!”的回复,说明运行成功.其中-XX:-UseCompressedOops参数是为了优化Java在Occlum下的启动时间;-Dos.name=Linux参数是告知JVM虚拟机LibOS系统类型;图(1)SpringBoot启动示意图整个SpringBoot网络服务的运行过程都是在保密的计算环境中进行的。ECS实例自带的底层软件无权窥探被保护的服务,实现了云上服务的运行数据保护。神龙架构第七代ECS与Java机密计算阿里云发布的神龙架构第七代ECS实例搭载Intel第三代XeonScalable处理器(代号IceLake)。这款处理器提供的下一代英特尔SGX安全技术(SGX2)在核心数量和EPC内存容量上都有非常可观的提升。具体规格见图(2)。IceLake处理器在核心数上提供了最高80个物理核心(160个逻辑核心)的处理能力,而第一代SGX可用的处理器只有最多6个物理核心;EPC内存容量增加到1TB,而第一代SGXEPC内存容量只有128M。用户可根据需要选择不同规格的内核数和EPC内存容量。图(2)SGX技术规格对比图由于SGX1提供的EPC内存容量和核心数太少,不适合Java等比较重的编程语言。长期以来,只有C/C++等原生语言更适合在SGX1中运行。另外,SGXSDK定义的HostEnclave编程模型需要对业务代码进行划分,对代码的侵入性较大,进一步限制了SGX1的使用范围。由于SGX2技术在核心数和EPC内存容量上的提升,我们可以突破HostEnclave编程模型的束缚,同时满足Java服务对硬件资源的要求。基于SGX部署Java机密计算服务成为可能,公有云计算可期。该场景下的机密计算服务将迎来蓬勃发展。ConfidentialComputingModelConfidentialComputingProgrammingModelConfidentialComputing主要有两种编程模型,如图(3)所示:图(3)ConfidentialComputingProgrammingModel一种是Host-Enclave编程模型,将整个应用分为Host和EnclaveEnclave有两部分。Host运行在一个公共环境中,负责大部分的应用逻辑处理。只是将一些需要安全保护的业务逻辑(比如加解密)放到enclave环境中执行,通过ecall和ocall操作实现两者之间的切换和信息传递;在这种编程模型下,用户需要将业务分为Host和Enclave两部分进行编程,还需要编写ecall(ocall)代码实现Host和Enclave之间的切换和信息交互,编程和改造难度大现有业务也存在一定困难。但优点是EnclaveTCB足够小,安全级别高。//enclave.cintfunction(inta,intb){returna+b;}//host.cintmain(){......enclaveec=create_enclave();intc=function(&飞地,3,5);销毁飞地(EC);......printf("sumis:%d\n",c);}另一种是Full-Feature编程模型,将整个完整的应用程序放在Enclave中运行,Host只负责Enclave管理和ocall操作,一般由底层框架的工具链提供,用户无需感知Host的存在;这种编程模型与传统的编程模型一致,不需要切分,也没有额外的编程难度,修改现有的业务代码也非常容易。但是,这种模型需要一个强大的SDK或LibOS驻留在enclave中,以支持整个应用程序的正常运行。另外,业务代码本身的规模会导致enclave中的TCB很大,安全级别会降低。//App.cintfunction(inta,intb){returna+b;}intmain(){intc=function(3,5);printf("总和是:%d\n",c);}两种保密计算编程模型各有优缺点,用户需要在易用性和安全性这两个指标中做出权衡。机密计算需求模型不可能鱼和熊掌兼得,需要在易用性和安全性这两个需求维度之间进行权衡。我们按照安全级别对机密计算业务需求进行分类,针对不同的安全级别选择不同的编程模型,如图(4)所示。当业务中只有少量计算逻辑需要安全保护,且安全级别要求高时,可选择Host-Enclave编程模型;当用户不想对业务代码进行大量改动,并且可以接受相对较低的安全级别时,可以选择Full-Feature编程模型。图(4)机密计算需求模型SGX机密计算软件生态神龙架构第七代ECS实例提供的第二代SGX技术在硬件能力上没有瓶颈。那么在接下来的一段时间内,新交所技术软件生态系统的发展将决定新交所技术能否得到广泛应用并产生商业价值。SGXSDKIntel在发布第一代SGX技术时推出了IntelSGXSDK,为C/C++语言定义了SGX机密计算Host-Enclave编程模型,使用.edl文件定义了Host与Enclave的交互接口;随后微软云Azure推出了OpenEnclave,它是IntelSGXSDK的功能扩展和平台抽象。可以在Enclave中运行更复杂的业务,同时扩展对安全计算硬件平台(SGX和TrustZone等)的支持;GoogleCloud推出了Asylo编程模型,类似OpenEnclave,同样进行平台抽象和功能扩展。Asylo最大的特点是将Encalve抽象为远程服务,通过GRPC与Host进行交互。它可以让Host和Enclave这两个模块在物理上分离,不局限于一个芯片,也屏蔽了Host和Enclave之间的编程语言差异,使得Asylo的编程模型更加灵活,非常有借鉴意义。纵观IntelSGXSDK、OpenEnclave和Asylo的发展,不难看出OpenEnclave和Asylo是对IntelSGXSDK的继承和发展。以上三个SDK满足了一些机密计算应用场景,比如用C/C++语言编写,只有少数需要安全防护的计算业务场景。由于EnclaveSDK能力的限制,无法支持复杂的Enclave业务逻辑。主要特点如下:均属于Host-Enclave编程模型,Asylo也在一定程度上支持Full-Feature编程模型;开发难度大,Host-Enclave编程模型需要划分应用程序;只支持C/C++编程语言,不能支持Java/Go等高级编程语言;不支持Full-Feature编程模型,无法满足易用性要求高的业务场景;SGXLibOSSGX运行环境与普通运行环境有很多不同,是否可以在Enclave中引入一个OS来屏蔽SGX执行环境的差异,让应用感知不到SGX的存在,就像在正常运行一样环境?业内有很多这样的先驱。目前比较知名的SGXLibOS项目有Occlum、Graphene和SGX-LKL等,其中Occlum是Ant开发的开源TEE-OS系统。它使用Rust编程语言,功能比较完善。它支持多种编程语言,同时还具有高性能和内存安全的特点。SGXLibOS的目的是让整个应用程序在SGXEnclave中方便的运行,符合Full-Feature机密计算编程模型,易用性高,支持多种编程语言和复杂的应用程序。该方案主要存在以下问题:TCB增加,牺牲了一定的安全性;需要消耗更多的SGX硬件资源;频繁的ecall和ocall操作(如IO)影响业务性能;AlibabaDragonwell机密计算SGX1有一个核心,但是由于数据和EPC大小的限制,如果在LibOS平台上部署对内存需求大、逻辑复杂的应用程序,不可避免地会出现频繁的EPC内存交换和ecall(ocall)切换,导致业务性能严重下降,难以投入生产环境。因此,SGX1的硬件条件决定了它只能支持用C/C++编程语言实现的简单飞地业务场景。随着神龙架构第七代ECS实例的发布,在SGX2时代之后,得益于核心数量和EPC内存大小的提升,基于Java编程语言的机密计算服务已经具备了实际条件。Java机密计算解决方案阿里巴巴Java虚拟机团队推出的Java机密计算解决方案如图(5)所示。本方案采用Full-Feature编程模型,通过在Enclave中引入LibOS支持AlibabaDragonwell11运行,上层应用不感知SGX环境。图(5)AlibabaDragonwell,Java机密计算解决方案,是阿里巴巴Java虚拟机团队对OpenJDK的开源实现。目前支持8和11两个LTS版本。针对AlibabaDragonwell11,发布了兼容glibc和musllibc的JDK版本,目的是让AlibabaDragonwell11适配更多的LibOS。由于musl比glibc轻量,而且代码易于维护,所以在机密计算领域比较流行。许多LibOS更喜欢将musl作为支持的基础库(例如Occlum)。AlibabaDragonwell11musl版不仅可以作为机密计算的首选JDK版本,还可以用来构建Alpine容器镜像,有效降低容器镜像的体积。Java机密计算性能评估性能是一个绕不开的话题。Java业务在SGX2中运行性能如何?我们对JavaSpringBoot业务在SGX1/SGX2/Linux三种运行环境下的性能进行了压力测试。设置相同的测试压力(并发数400,压力测试时间40s),从系统吞吐量(MB/s)和RPS(requests/s)两个压测指标维度进行对比分析。压测结果如图(6)所示:图(6)Java机密计算SGX压测性能对比图在相同的测试压力下,Linux平台的吞吐量为26.91MB/s,RPS为12.84K/;SGX2吞吐量为18.53MB/sec,RPS为8.84K/sec;SGX1的吞吐量为1.26MB/秒,RPS为602.10K/秒。可以看出SGX2相比SGX1取得了巨大的性能提升,但是与Linux平台还是有一定的差距。相信随着AlibabaDragonwell11的不断优化,性能会进一步提升。总结在阿里云发布神龙架构第七代ECS实例后,阿里巴巴Java虚拟机团队提出了Java语言的机密计算编程模型和解决方案,并进行了深入实践,发布了阿里云Java机密计算.Dragonwell11JDK版本。从实际结果来看,基于SGX2的Java机密计算解决方案在性能上有显着提升,可以支持复杂的Java机密计算业务的稳定运行。相信基于SGX2的Java机密解决方案将有力推动Java机密计算的发展。希望对Java机密计算感兴趣或有需求的开发者试用我们的方案,期待与您进一步交流。原文链接本文为阿里云原创内容,未经许可不得转载。