菜鸡葫芦娃 发表于 2017-3-24 21:06

记一银行木马逆向分析

本帖最后由 Hoimk 于 2017-4-4 12:53 编辑

报告名称:记一银行木马逆向分析
作者:Hoimk
报告更新日期:2017-3
样本发现日期:2017-2-11
样本类型:恶意拦截钓鱼样本文件
可能受到威胁的系统:Android

N天前别人发给我让我分析的..刚找了半天样本没找到,好像被我删了~so,没有down

踩点
首先我拿到这个包的时候名字是ok_killer…也就是说,已经被重打包过了,可能被修改或删减了部分功能
1. 先以压缩包打开
      根目录:


      

      嗯…看到各种mail服务的文件,典型的邮箱收信。

      Assets:
      
      
      
      有两个文件,目测是动态加载,暂时不管。
      Lib下:

      

      有一个so,只有arm构架的…

2.Apktool d反编译,先打开AndroidManifest.xml看看
<uses-permission android:name="android.permission.VIBRATE"/>
<…一系列监听权限>
<application
android:allowBackup="true"
android:debuggable="true"
android:icon="@drawable/icon1"
android:label="@string/app_name"
android:name="com.exp.wr.AaApp">
      <activity
            android:excludeFromRecents="true"
            android:label="@string/app_name"
            android:name="com.qwe.MainActi">
            <intent-filter>
                <action android:name="android.intent.action.MAIN"/>
                <category android:name="android.intent.category.LAUNCHER"/>
            </intent-filter>
      </activity>
      <activity
            android:excludeFromRecents="true"
            android:name="com.qwe.Bridg"
            android:theme="@android:style/Theme.NoTitleBar.Fullscreen">
            <intent-filter>
                <action android:name="android.intent.action.MAIN"/>
            </intent-filter>
      </activity>
      <activity
             android:name="com.qwe.Act"
             android:screenOrientation="portrait" android:windowSoftInputMode="stateAlwaysVisible"/>
      <activity android:name="com.qwe.C_LLL" android:screenOrientation="portrait"/>
      <activity
             android:name="com.qwe.SB_CCC"
             android:screenOrientation="portrait"
             android:windowSoftInputMode="stateAlwaysVisible"/>
      <activity
             android:configChanges="keyboardHidden|navigation|orientation"
             android:exported="true"
             android:name="com.qwe.Secu"
             android:screenOrientation="portrait"/>
      <activity
             android:configChanges="keyboardHidden|navigation|orientation"
             android:name="com.qwe.TakePhoto"
             android:screenOrientation="portrait"/>
      <activity
             android:name="com.qwe.Fi"
             android:screenOrientation="portrait"
             android:theme="@android:style/Theme.NoTitleBar.Fullscreen"/>
      <receiver
             android:description="@string/app_name"
             android:label="@string/app_name"
             android:name="com.a.MyAdminReceiver"
             android:permission="android.permission.BIND_DEVICE_ADMIN">
            <meta-data android:name="android.app.device_admin" android:resource="@xml/god"/>
            <intent-filter>
                <action android:name="android.app.action.DEVICE_ADMIN_ENABLED"/>
            </intent-filter>
      </receiver>
      <receiver android:enabled="true" android:exported="true" android:name="com.a.Boo">
            <intent-filter android:priority="2147483647">
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
                <action android:name="android.intent.action.ACTION_SHUTDOWN"/>
                <action android:name="android.intent.action.USER_PRESENT"/>
            </intent-filter>
      </receiver>
      <receiver android:name="com.a.A113">
            <intent-filter android:priority="2147483647">
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
                <…一系列监听事件>
                <category android:name="android.intent.category.HOME"/>
            </intent-filter>
      </receiver>
      <service android:enabled="true" android:name="com.qwe.service.AutBan" android:persistent="true">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
            </intent-filter>
      </service>
      <service android:enabled="true" android:name="com.qwe.service.SM" android:persistent="true">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
            </intent-filter>
      </service>
      <service android:enabled="true" android:name="com.qwe.service.Inte" android:persistent="true">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
            </intent-filter>
      </service>
      <service android:enabled="true" android:name="com.qwe.service.InLit" android:persistent="true">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
            </intent-filter>
      </service>
      <service android:enabled="true" android:exported="true" android:name="com.qwe.service.UploadServ" android:persistent="true">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
            </intent-filter>
      </service>
      <service android:enabled="true" android:name="com.qwe.service.Heart" android:persistent="true">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED"/>
            </intent-filter>
      </service>
    </application>
</manifest>
可以看到注册了一个Application类,和一系列自启动的服务,其中有一个服务监听了启用设备管理器的事件。


分析
既然注册了Application,那自然是从Application类入口,所以先看com.exp.wr.AaApp。
onCreate里没有内容,attachBaseContext里调用了loadNsClass方法:




看这方法名字就知道是动态加载啦,全程调用反射的方法来复制Assets下的ac文件,然后将其解密,加载,最后删除。
解密方法:





嗯..跑一下,得到这个:





baksmali d classes.dex,得到smali代码,合并到apktools反编译出来的smali文件夹里,smali a smali 重打成Dex。
现在类就全了:






然后再说一下那个Util.hasMore方法,这是个native方法,也就是那个libutil_jni.so里的方法。
没有类对应函数名,.init也没有内容,看JNI_OnLoad:









嗯…并没有什么卵用。OK,接下来就是Launcher Activity,
MainActi OnCreate:



233333,第一眼看到了邮箱账号密码,就是….



那个网页也打不开,可能是只允许某个国家的IP访问~
行,先看看那个getBankInfo,他的作用是查找手机里安装了哪些银行APP:



public static String[] BK_PACK_LIST = new String[]{
"com.epost.psf.sdsi",
"com.knb.psb",
"com.cu.sb",
"com.shinhan.sbanking",
"nh.smart",
"com.kbstar.kbbank",
"com.areo.bs",
"com.smg.spbs",
"com.ibk.neobanking",
"com.keb.android.mbank",
"com.hanabank.ebk.channel.android.hananbank"};

嗯~ 这些都是韩国的银行APP~
然后他启动了好几个服务,这个稍后再逐个分析,来看看他怎么激活任务管理器的,这个蛮有意思,
申请激活任务管理器:



注意了,这个createSmallWindow方法,就是在屏幕上创建一个悬浮窗,而这个悬浮窗是长这样的~



有没有懂?左边的按钮是取消,右边是确定,对应着被遮挡住的激活窗口,确定下面就是激活,so,点了确定就=点了激活~激活之后系统应该是发出广播了,吓得我急忙打开了com.a.MyAdminReceiver类,然而这竟然是个空类..WTF..不过之后执行了一个隐藏桌面图标的操作



没事,我们还有好多个服务呢,一个个看
[*]Inte:
      
      

      

      接到某个电话立马挂掉+删除记录。

[*]AutBan:
      

      判断现在最顶层的Activity是否为属于银行的APP
      JudgeAV是判断手机里是否安装了韩国杀软 安博士

      

      卸载安博士..

      .

      利用Wake_Lock机制使服务常驻内存,
      还有一个线程,也是判断安装列表,这四个都是1秒循环执行。我们看判断到activity后他的劫持动作,即com.qwe.Bridg
      先显示出来一个这个:
      
      …假装是个杀毒插件吗,最后跳到了这个界面:
      
      

      
      嗯,你懂的...
      等你填完信息以后,启动UploadServ这个服务,
      还把信息打包成zip~


      

      然后POST上传:
               
      嗯..也就是上边那个网址+ /servlet/UploadDoc/

               
      最后发送邮件

[*]SM(Send Message 能不能换个正常点缩写):

      
      
      嗯…从/appHome/servlet/GetMessage请求群发短信内容,然后遍历联系人列表群发,这个操作是45分钟一次

[*]Heart:

      
      
      发送银行信息 + 设备信息至Web端,此操作只执行一次。

      

      重发资料至邮件

      

      发送..心跳包。。。。

      

      上传通讯录

这些服务都有一个newWakeLock。

整理
[*]首先,使用一个外壳来动态加载核心代码,且使用反射技术来躲避安全软件的检测。
[*]随后,启动相关服务并申请激活设备管理器,并显示一个是否更新的悬浮窗来遮挡窗口,欺骗点击激活按钮
[*]隐藏桌面图标
[*]利用Wake_Lock机制,使服务常驻内存
[*]检测杀软(安博士),并实时卸载杀软(阻止安装)
[*]群发钓鱼短信
[*]实时检测当前Activity,劫持银行APP
[*]使用Web服务端来进行动态修改群发短信内容及接受数据
[*]从心跳包上看,Web服务端可能有一套完善的系统


最后..有没有大佬招实习小弟啊...

dyj 发表于 2017-3-25 00:18

感觉很牛逼的样子!

A00 发表于 2017-3-24 21:28

支持,很不错的文章

l281180570 发表于 2017-3-24 21:31

不得了,赞一个

恶梦玩家 发表于 2017-3-24 22:16

新手,学习学习

qgz0007 发表于 2017-3-24 22:20

一堆的韩文,这个是国外的玩意吧

jack300 发表于 2017-3-24 22:26

高手太牛了

orient2012 发表于 2017-3-25 00:08

我很赞同!

muyubaby 发表于 2017-3-25 00:22

最后发送邮件

爱生活爱晴天 发表于 2017-3-25 03:34

太厉害了,赞{:1_918:}
页: [1] 2 3 4 5 6 7 8 9 10
查看完整版本: 记一银行木马逆向分析