abraxaslabs.tech · github.com/abraxas · @abraxas_null · [email protected] · element-fragment-guest
解説記事: https://abraxaslabs.tech/research/element-fragment-guest
Element Web v1.12.29 - Element / New Vector
分類: セッション破壊 到達範囲: リモート
Lifecycle.loadSession は restoreSessionFromStorage よりも URL ハッシュ内の guest_user_id と guest_access_token を優先します。ゲストはデフォルトで有効です(enableGuest={!config.disable_guests})。app.element.io の config.json は disable_guests を設定していません。onTokenLoginCompleted は SSO と OIDC のパラメータのみを除去します。ゲストキーは決して除去しません。url_utils.ts は既に、これらのフラグメントパラメータは未使用に見えるとコメントしています。それでもこれらが優先されます。
サインイン済みユーザーにゲストフラグメントパラメータ付きのハッシュ URL を開かせることができる者は誰でも、そのユーザーをログアウトさせ、ローカルの暗号を消去させます。ゴミトークンで十分です。whoami は決して呼ばれません。
| ID | CVE 未割当 |
| CWE | CWE-384 / CWE-352 / CWE-613 |
| CVSS | High: 7.1 CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:H |
| 製品 | Element Web |
| 影響を受けるバージョン | v1.12.29 タグ v1.12.29 (2d90d6b7b601ecb9ccdf81239a43b4396b4b0c9e)。ゲスト有効(デフォルト)。 |
| 認証 | 未認証の攻撃者。被害者は URL を開く(または再読み込みする)必要がある。 |
| ライセンス | GNU Affero GPL v3.0 |
| ラボ | 127.0.0.1 のみ |
サインイン済みユーザーにゲストフラグメントパラメータ付きのハッシュ URL を開かせます。クライアントはそのユーザーをログアウトさせ、ローカルの暗号を消去し、攻撃者のゲストに配置する可能性があります。これはログアウトと暗号の消去です。本物のトークンを盗むものではありません。OS の RCE でもありません。
| 権限 | メソッド / シンク | 偵察 / 完全性 / 可用性 | ラボ実証または推測 |
|---|---|---|---|
| ハッシュからゲスト資格情報を解析 | url_utils.ts guest: { keys: ["guest_user_id", "guest_access_token"], location: "fragment" } | セッション選択の完全性 | ラボ実証済み。#/home?guest_user_id=...&guest_access_token=... は guest_params になった。クエリ文字列のみではならなかった。 |
| 保存された非ゲストセッションよりゲストを優先 | Lifecycle.loadSession のゲスト優先分岐、ログ Using guest access credentials | 完全性 | ラボ実証済み。シードされた @victim:example.org は復元されなかった。 |
| localStorage、IndexedDB アカウント、sessionStorage、暗号を消去 | doSetLoggedIn(..., clearStorageEnabled=true) の後に clearStorage() | ローカルセッションの完全性 / 可用性 | ラボ実証済み。crypto_empty=yes、以前のトークンは消えた。 |
| トークン検証をスキップ | ゲスト経路は /_matrix/client/v3/account/whoami を決して呼ばない | 完全性 | ラボ実証済み。whoami_called=no。ゴミトークン not-a-real-token でも消去された。 |
| 攻撃者のゲスト資格情報を永続化 | 消去後の persistCredentials | 完全性 | ラボ実証済み。after_user=@x:example.org、after_token=not-a-real-token、mx_is_guest=true。 |
| デフォルト HS 上の実ゲストに固定 | ゲストトークンが有効な場合の同じ persist | 完全性 | 推測。ラボはゴミトークンを使用したため、ライブ HS ログインはなし。 |
| 再読み込み時にもこれを継続 | ゲストキーはハッシュに残る。onTokenLoginCompleted はそれらを削除しない | 完全性 | ピン app.tsx からの推測。ラボは URL を一度開いた。 |
この残りについては結論が出ています。実際のアクセストークンを窃取すること(それは削除されるのであり、持ち出されるのではない)。OS RCE / LPE(Desktop の nodeIntegration: false、sandbox)。ライブの Element SPA(how=gadget)。クエリ文字列 ?guest_user_id=(フラグメントのみ)。disable_guests: true は非ゲストセッションを維持します。非ゲストセッションが存在する場合にゲストを無視するようパッチを当てた loadSession も、それを維持します。
同じピンにおける残件:vector: Windows ドライブレター、Univention ICS javascript: href。
2026年9月22日の GitHub リリース後、Element Web v1.12.29 をピン留めしました。SSO の loginToken はクエリ専用で、使用後に除去されます。ゲストキーは依然としてフラグメント内に残り、リストアよりも優先されます。url_utils.ts 内のコメントがその証拠です。彼ら自身、これらのキーが仕様化されていることに疑念を抱いていました。
すでに記録済みの誤った道筋:クエリ文字列 ?guest_user_id= をベクターとみなすこと(キーはハッシュ内に存在する)。これをトークン窃取と呼ぶこと(実際のトークンは送信されるのではなく削除される)。app.element.io の設定に disable_guests があると期待すること(それは未設定である)。リバースシェル。茶番です。
ピン留めした関数のガジェット。ライブの Element Web コンテナではありません。how=gadget。
python3 element-fragment-guest-Abraxas-Labs.py
または
cd lab
./run.sh
対象は http://127.0.0.1:19600 のみです。プロジェクト element-fragment-guest を構成します。実行後、スタックは破棄されます。
SUCCESS element-fragment-guest how=gadget guest-wipe=yes prior-kept=no garbage-token=yes disable-guests-keeps=yes ELEMENT-FRAGMENT-GUEST-WITNESS
非ゲストセッションがすでに存在する場合、ゲストのフラグメントパラメータを無視します。clearStorage の前に /_matrix/client/v3/account/whoami でゲストトークンを検証します。SSO トークンが除去されるのと同じ方法で guest_user_id と guest_access_token を除去します。ホストされている app.element.io では disable_guests: true をデフォルトにします。
Lifecycle.ts(loadSession のゲスト優先処理)url_utils.tsapp.tsx(enableGuest={!config.disable_guests})GNU Affero GPL v3.0。LICENSE を参照してください。ループバックラボ専用です。保証はありません。