AI繁荣下的隐忧——Google Tensorflow安全风险剖析

本文由云+社区发表node

做者:[ Tencent Blade Team ] Cradminpython

img

咱们身处一个巨变的时代,各类新技术层出不穷,人工智能做为一个诞生于上世纪50年代的概念,近两年出现井喷式发展,获得各行各业的追捧,这背后来自于各类力量的推进,诸如深度学习算法的突破、硬件计算能力的提高、不断增加的大数据分析需求等。从2017年的迅猛发展,到2018年的持续火爆,国内外各个巨头公司如腾讯、阿里、百度、Google、微软、Facebook等均开始在人工智能领域投下重兵,毫无疑问,这一技术将来将会深度参与咱们的生活并让咱们的生活产生巨大改变:人工智能时代来了!git

面对一项新技术/新趋势的发展,做为安全研究人员该关注到什么?没错,每个新技术的诞生及应用都会伴随有安全风险,安全研究人员要在风暴来临以前作到未雨绸缪。github

Blade Team做为关注行业前瞻安全问题的研究团队,天然要对AI技术进行安全预研。算法

img

一个典型的人工智能系统大体由3部分组成:算法模型,AI支撑系统(训练/运行算法的软件基础设施)和业务逻辑及系统。好比一我的脸识别系统基本架构以下:shell

img

图1:典型人脸识别系统架构api

从安全视角来看,咱们能够得出3个潜在的攻击面:安全

AI算法安全:算法模型是一个AI系统的核心,也是目前AI安全攻防对抗的焦点。具体来说,目前AI算法安全的主要风险在于对抗样本(adversarial examples)攻击,即经过输入恶意样原本欺骗AI算法,最终使AI系统输出非预期的结果,目前已发展出诸如生成对抗网络(GAN)这种技术[0],以AI对抗AI,在这个领域学术界和工业界已有大量研究成果,你们可Google了解。性能优化

AI支撑系统安全:AI算法模型的运行和训练都须要一套软件系统来支撑,为了提升计算效率和下降门槛,各大厂商开发了机器学习框架,本文的主角Google Tensorflow就属于这一层,类比于计算机系统中的OS层,能够想象到这里若是出现安全问题,影响如何?而这类框架的安全性目前并无获得足够的关注。bash

业务逻辑系统:上层业务逻辑及相关系统,与传统业务和运维安全风险差异不大,再也不赘述。

img

通过近几年的发展,各类机器学习框架不断涌现出来,各有特点,其中不乏大厂的身影,咱们选取了三款使用量较大的框架做为研究对象:

Tensorflow[1]:由Google开发,面向开源社区,功能强大,易用性高,早期性能稍差,但在Google强大的工程能力下,已有明显改观,从使用量上看,目前是机器学习框架里面的TOP 1。

Caffe[2]:2013年由UC Berkely的贾扬清博士开发,在学术界使用极其普遍,卷积神经网络的实现简洁高效,但因历史架构问题,不够灵活。目前贾教主已就任Facebook,并在Facebook的大力支持下,推出了Caffe2,解决Caffe时代留下的问题(编辑注:发布本文时,已有消息称贾教主已经加盟阿里硅谷研究院,可见巨头对AI人才的渴求)。

Torch[3]:Facebook内部普遍使用的一款机器学习框架,灵活性和速度都不错,惟一不足是默认采用Lua语言做为API接口,初学者会有些不习惯,固然目前也支持了Python。

img

图2 业界流行机器学习框架简要对比

以Tensorflow为例,咱们先来看一下它的基本架构:

img

图3 Tensorflow基本架构[4]

由上图大体能够看出,除了核心的机器学习算法逻辑外(Kernel implementations),Tensorflow还有大量的支撑配套系统,这无疑增长了软件系统的复杂性。

咱们继续沿用上一节的思路,首先详细分析下Tensorflow的攻击面。这里也插个题外话,分享下我的的一些研究习惯,通常在接触到一个新领域,笔者习惯通读大量资料,对该领域的基本原理和架构有个相对深刻的了解,必要时结合代码粗读,对目标系统进行详细的攻击面分析,肯定从哪一个薄弱点入手,而后才是看我的喜爱进行代码审计或Fuzzing,发现安全漏洞。在笔者看来,安全研究前期的调研工做必不可少,一方面帮你肯定相对正确的研究目标,不走过多弯路,另外一方面对功能和原理的深刻理解,有助于找到一些更深层次的安全问题。

经过对Tensorflow功能和架构的了解,笔者大体把攻击面分为如下几类:

*输入文件解析逻辑:包括对训练和推断时用到的图片、视频、音频等类型文件的解析处理*

*模型处理逻辑:模型文件的解析和模型运行机制*

*机器学习算法逻辑:机器学习算法实现逻辑*

*分布式部署及扩展功能:包括Tensorflow分布式集群功能,性能优化XLA Compiler,自定义函数扩展功能等。*

详细可参考下图,这是当时基于Tensorflow 1.4版本的分析,有兴趣的读者能够自行分析添加。在随后的审计中,咱们在多个攻击面中发现了安全问题,其中一个最严重的风险存在于Tensorflow的模型处理机制。

img

图4 Tensorflow攻击面分析

img

咱们先来了解下Tensorflow的模型机制。

顾名思义,Tensor是Tensorflow中的基本数据类型(或者说数据容器),flow表示dataflow,Tensorflow用数据流图(dataflow graph)来表示一个计算模型,图中的结点(node)表示计算操做(operation),图中的边(edge)表示数据输入和输出,当咱们设计了一个机器学习模型,在Tensorflow中会以一张数据流图来表示,最终算法模型会以图的形式在Tensorflow运行时(runtime)下执行,完成咱们须要的运算。能够参考Tensorflow官网的一个示例。

img

图5 Tensorflow的数据流图[5]

机器学习模型训练中常常会出现这样的场景:

1) 须要中断当前训练过程,保存模型,以备下次从中断处继续训练

2) 把训练好的模型保存,分享给他人进一步调优或直接使用

Tensorflow提供了两种种模型持久化机制,能够把算法模型保存为文件:tf.train.Saver和tf.saved_model。两组API在把模型持久化为文件时,结构上有些差别,tf.train.Saver适合临时保存被中断的训练模型,被保存的模型称为一个checkpoint,tf.saved_model更适合保存完整的模型提供在线服务。

tf.train.Saver保存的模型文件以下:

img

savermodel.meta是模型的元数据,也就是数据流图的描述文件,采用特定的二进制格式,savermodel.data-xxx保存着模型中各个变量的值。

再来看下tf.saved_model保存的模型文件:

img

img

saved_model.pbtxt保存着表示算法模型的图结构,能够指定保存为protobuf文本格式或二进制格式,但一般状况下出于空间效率考虑,默认采用二进制形式保存,variables目录中保存模型中变量的值。

能够看到,无论哪一种方式,都须要保存关键的数据流图的结构,打开saved_model.pbtxt,仔细看下咱们关心的数据流图:

img

能够比较直观的看到图的结构,好比Add是操做类型,输入是参数x和y,输出是z,不可贵出是一个简单的加法计算z=x+y;Tensorflow API提供了大量的操做类型,来知足各类计算需求。

img

图6 Tensorflow Python API[6]

看到这里,你们可有什么想法?没错,既然算法模型是以图的形式在Tensorflow中执行,从图的角度看,咱们可否在不影响图的正常流程的状况下,插入一些额外的操做(结点)呢?进一步,若是这些操做是恶意的呢?

img

从上一节的分析,咱们发现了一个让人略感兴奋的攻击思路,在一个正常的Tensorflow模型文件中插入可控的恶意操做,如何作到呢?须要知足两个条件:

1)在数据流图中插入恶意操做后,不影响模型的正常功能,也就是说模型的使用者从黑盒角度是没有感知的;

2)插入的操做可以完成“有害”动做,如代码执行等。

先看下第二个条件,最直接的“有害”动做,通常可关注执行命令或文件操做类等,而Tensorflow也确实提供了功能强大的本地操做API,诸如tf.read_file, tf.write_file, tf.load_op_library, tf.load_library等。看这几个API名字大概就知其义,最终咱们选择使用前2个读写文件的API来完成PoC,其余API的想象空间读者可自行发掘。在验证过程当中,笔者发现这里其实有个限制,只能寻找Tensorflow内置的API操做,也叫作kernel ops,若是是外部python库实现的API函数,是不会插入到最终的图模型中,也就没法用于这个攻击场景。

知足第一个条件,并无想象的那么简单,笔者当时也颇费了一翻周折。

咱们以一个简单的线性回归模型y=x+1为例,x为输入变量,y为输出结果,用Tensorflow的python API实现以下:

img

读写文件类的操做显然与线性回归计算无关,不能直接做为模型的输入或输出依赖来执行;若是直接执行这个操做呢?

img

图7 tf.write_file API文档[7]

从tf.write_file API文档能够看到,返回值是一个operation,能够被Tensorflow直接执行,但问题是这个执行如何被触发呢?在Tensorflow中模型的执行以run一个session开始,这里当用户正常使用线性回归模型时,session.run(y)便可获得y的结果,若是要执行写文件的动做,那就要用户去执行相似session.run(tf.write_file)这样的操做,显然不正常。

在几乎翻遍了Tensorflow的API文档后,笔者找到了这样一个特性:

img

图8 tf.control_dependencies API文档[8]

简单来讲,要执行control_dependencies这个context中的操做,必需要先计算control_inputs里面的操做,慢着,这种依赖性不正是咱们想要的么?来看看这段python代码:

img

这个success_write函数返回了一个常量1,但在control_dependencies的影响下,返回1以前必须先执行tf.write_file操做!这个常量1正好做为模型y=x+1的输入,漏洞利用的第一个条件也知足了。

最后还有一个小问题,完成临门一脚,可以读写本地文件了,能干什么“坏事”呢?在Linux下能够在crontab中写入后门自动执行,不过可能权限不够,笔者这里用了另一种思路,在Linux下读取当前用户home目录,而后在bashrc文件中写入反连后门,等用户下次启动shell时自动执行后门,固然还有其余利用思路,就留给读者来思考了。值得注意的是,利用代码中这些操做都须要用Tensorflow内置的API来完成,否则不会插入到图模型中。

把上面的动做串起来,关键的PoC代码以下:

img

当用户使用这个训练好的线性回归模型时,通常使用如下代码:

img

运行效果以下:

img

模型使用者获得了线性回归预期的结果4(x=3, y=4),一切正常,但其实嵌入在模型中的反连后门已悄然执行,被攻击者成功控制了电脑。

img

图9 Tensorflow模型中反连后门被执行

在完成这个PoC后,咱们仔细思考下利用场景,在Tensorflow中共享训练好的机器学习模型给他人使用是很是常见的方式,Tensorflow官方也在GitHub上提供了大量的模型供研究人员使用[9],咱们设想了这样一个大规模攻击场景,在GitHub上公布一些经常使用的机器学习模型,在模型中插入后门代码,而后静待结果。

回顾一下,这个安全问题产生的根本缘由在于Tensorflow环境中模型是一个具备可执行属性的载体,而Tensorflow对其中的敏感操做又没有作任何限制;同时在通常用户甚至AI研究人员的认知中,模型文件是被视做不具备执行属性的数据文件,更增强了这种攻击的隐蔽性。

咱们把这个问题报告给Google后,通过多轮沟通,Google Tensorflow团队最终不认为该问题是安全漏洞,但认为是个高危安全风险,并专门发布了一篇关于Tensorflow安全的文章[10],理由大体是Tensorflow模型应该被视做可执行程序,用户有责任知道执行不明模型的风险,并给出了相应的安全建议。

img

在对Tensorflow其余攻击面的分析中,咱们尝试了人工审计代码和Fuzzing的方法,又发现了多个安全漏洞,大部分属于传统的内存破坏型漏洞,涉及Tensorflow的图片解析处理、模型文件解析、XLA compiler等功能,而且漏洞代码都属于Tensorflow框架自己,也从侧面反映了Tensorflow在代码安全上并无作更多的工做。

下面是Tensorflow发布的安全公告及致谢[11],目前为止共7个安全漏洞,均为Tencent Blade Team发现,其中5个为笔者发现。

img

在研究过程当中,咱们也注意到业界的一些相似研究,如360安全团队对多款机器学习框架用到的第三方库进行了安全审计,发现存在大量安全问题[12],其中多为传统二进制漏洞类型。

img

回顾整个漏洞报告和处理流程,可谓一波三折。最初上报漏洞时,咱们发现除了GitHub上的issue,Tensorflow彷佛没有其余的漏洞上报渠道,出于风险考虑,咱们以为发现的安全问题在修复以前不适合在GitHub上直接公开,最后在Google Groups发帖询问,有一个自称是Tensorflow开发负责人的老外回复,能够把安全问题单发给他,开始笔者还怀疑老外是否是骗子,过后证实这我的确实是Tensorflow团队开发负责人。

通过持续近5个月、几十封邮件的沟通,除了漏洞修复以外,最终咱们也推进Google Tensorflow团队创建了基本的漏洞响应和处理流程。

1)Tensorflow在GitHub上就安全问题做了特别说明Using Tensorflow Securely[10],包括安全漏洞认定范围,上报方法(邮件报告给security@tensorflow.org),漏洞处理流程等;

img

图10 Tensorflow安全漏洞处理流程

2)发布安全公告,包括漏洞详情和致谢信息[11];

3)在Tensoflow官网(tensorflow.org)增长一项内容Security[13],并连接至GitHub安全公告,引导用户对安全问题的重视。

img

img

针对咱们发现的模型机制安全风险,Google在Using Tensorflow Securely这篇安全公告中作了专门说明[10],给出了相应的安全措施:

1)提升用户安全意识,把Tensorflow模型视做可执行程序,这里实际上是一个用户观念的转变;

2)建议用户在沙箱环境中执行外部不可信的模型文件,如nsjail沙箱;

3)在咱们的建议下,Tensorflow在一个模型命令行工具中增长了扫描功能(tensorflow/python/tools/saved_model_cli.py),能够列出模型中的可疑操做,供用户判断。

能够看出,Tensorflow团队认为这个安全风险的解决主要在用户,而不是Tensorflow框架自己。咱们也在Blade Team的官方网站上对这个风险进行了安全预警,并命名为“Columbus”[14]。

上文提到的其余内存破坏型漏洞,Tensorflow已在后续版本中修复,可参考安全公告[11]。

img

AI安全将走向何方?咱们相信AI算法安全的对抗将会持续升级,同时做为背后生产力主角的基础设施软件安全理应受到应有的关注,笔者但愿这个小小的研究能抛砖引玉(实际上咱们的研究结果也引发了一些专家和媒体的关注),期待更多安全研究者投身于此,一块儿为更安全的将来努力。

img

[0] en.wikipedia.org/wiki/Genera…

[1] www.tensorflow.org/

[2] caffe.berkeleyvision.org/

[3] torch.ch/

[4] www.tensorflow.org/guide/exten…

[5] www.tensorflow.org/guide/graph…

[6] www.tensorflow.org/versions/r1…

[7] www.tensorflow.org/versions/r1…

[8] www.tensorflow.org/versions/r1…

[9] github.com/tensorflow/…

[10] github.com/tensorflow/…

[11] github.com/tensorflow/…

[12] arxiv.org/pdf/1711.11…

[13] www.tensorflow.org/community#s…

[14] blade.tencent.com/columbus/

此文已由腾讯云+社区在各渠道发布

获取更多新鲜技术干货,能够关注咱们腾讯云技术社区-云加社区官方号及知乎机构号