当社のAIエンジンNeutronが、UCバークレーのCyberGymベンチマークで97.1%のスコアを記録しました。 詳細を見る

ディープダイブ

ディープダイブ

FreeRDP の RDP 中間者攻撃、3.32.2 で修正(CVE-2026-121392)

FreeRDP は 3.32.2 より前、2 つの独自実装による身元確認チェックでサーバー証明書を受け入れます。信頼された CA を持つ中間者が RDP セッションを傍受可能です。今すぐ更新を。

TL;DR

  • FreeRDP のクライアント側 TLS 身元確認は、Common Name が一致すれば Subject Alternative Names が一致しなくても証明書を受け入れ、IP リテラルの接続先を DNS 名と照合します。クライアントが信頼する CA の証明書を持つ中間者は、RDP セッションを傍受できます。
  • CVE レコードによると、3.32.2 より前のすべての FreeRDP リリースが対象です。これらのケースを記述した 2026 年 7 月のアドバイザリは、3 つのケースのうち 2 つに届かなかった 3.29.0 の修正を発表していました。
  • VulnCheck の CVE レコードは、この脆弱性を CVSS v4.0 で 9.1 Critical と評価しています。CVSS v3.1 では 7.4 High です。悪用は報告されておらず、2026 年 11 月 4 日時点で CVE は CISA の Known Exploited Vulnerabilities(KEV)カタログに載っていません。
  • 今すぐ FreeRDP 3.32.2 以降に更新してください。設定による回避策は文書化されていません。FreeRDP を組み込んだ製品については「修正するには?」を参照してください。

影響を受けるのは?

次の条件がすべて成り立つとき露出します:

  • FreeRDP ベースのクライアント、または FreeRDP を組み込んだ製品を 3.32.2 より前のバージョンで実行している。CVE レコードは初回リリース以降の全バージョンを対象としています。
  • 攻撃者が RDP の TCP 接続を傍受またはリダイレクトでき、クライアントが信頼する CA に連なる証明書を提示できる。アドバイザリが挙げるシナリオは、誤発行する公開 CA、侵害されたか不正なプライベート CA、その他の証明書信頼連鎖の異常です。
  • クライアントがサーバー証明書を検証している。元の開示は AutoAcceptCertificate = FALSE、AutoDenyCertificate = TRUE、AuthenticationLevel = 2 でこれらの脆弱性を再現しました。

信頼できる証明書を入手できない攻撃者は、この脆弱性の恩恵を受けません。この欠陥は信頼された CA のシナリオにおけるサーバー身元確認を弱めます。信頼そのものを作り出すわけではありません。

バージョン 対象 修正バージョン
3.32.1 とそれ以前の全リリース はい(デフォルトの身元確認) 3.32.2、2026-10-12 リリース
3.32.2 以降(3.33.0 を含む) いいえ 更新を継続

3.32.2 と 3.33.0 には新しい IP 確認に既知の欠陥が 1 つありますが、安全側に失敗します。不正な照合を受け入れるのではなく、正しい照合を拒否します(「なぜ修正は機能するか?」を参照)。

実行環境を確認:

# The FreeRDP 3 client front-ends all print the version
xfreerdp3 --version

# Debian-family package installs
dpkg -l | grep freerdp

# Library copies, including those bundled inside other products
ldconfig -p | grep libfreerdp

FreeRDP を組み込んだ製品は、その製品自身の更新が必要です。製品が報告するバージョンが、アドバイザリと照合すべきものです。

修正するには?

  1. FreeRDP 3.32.2 以降に更新します。修正コミットは 2026 年 10 月 12 日にリリースされた 3.32.2 に入り、以降の全リリースがそれを含みます。
  2. FreeRDP を組み込んだ製品は、ベンダーが修正済みライブラリを公開したら更新します。CVE レコードの対象範囲は初回リリースから始まるため、より古い組み込みコピーも対象です。
  3. クライアントが信頼する証明書を持つ傍受者を経由した可能性のあるセッションは、侵害済みとして扱ってください。そのような攻撃者は画面内容、キーストローク、クリップボードを見ることができ、入力を注入できます。そのセッションで使ったすべての認証情報を変更し、セッション内で行われた操作を確認してください。この脆弱性は攻撃者にそのネットワーク上の位置を与えるものではなく、すでにその位置にいる攻撃者がセッション内で操作できるようにするものです。

設定による回避策は文書化されていません。不完全な修正を発見した追跡アドバイザリは緩和策を提案していません。3.32.2 が実装したのは、このアドバイザリが提案した修正です。Common Name は DNS SAN が存在しないときにのみ考慮され、IP の接続先は iPAddress SAN エントリとのみ照合されます。FreeRDP はこのロジックを、OpenSSL の X509_check_host() と X509_check_ip_asc() を呼び出さずに独自に実装しました。アドバイザリによれば、この 2 つの関数も同じ規則を適用します。

根本原因は何か?

FreeRDP は、OpenSSL の長さを考慮した身元検証 API を使わず、独自の Common Name と DNS SAN の文字列照合を行っています。tag 3.32.1 における libfreerdp/crypto/tls.c の 1859~1879 行目の脆弱なブロック:

/* compare against common name */

if (common_name)
{
    if (tls_match_hostname(common_name, common_name_length, hostname))
        hostname_match = TRUE;
}

/* compare against alternative names */

if (dns_names)
{
    for (size_t index = 0; index < dns_names_count; index++)
    {
        if (tls_match_hostname(dns_names[index], dns_names_lengths[index], hostname))
        {
            hostname_match = TRUE;
            break;
        }
    }
}

このブロックの 2 つの性質が、サーバー身元確認を壊しています:

  • Common Name の確認と DNS SAN の確認が無条件の OR になっています。RFC 6125 の 6.4.4 節は逆を要求します。証明書が dNSName SAN エントリを 1 つでも持つとき、Common Name は無関係です。CN=rdp01.corp.example で、SAN リストが DNS:files.corp.example のように一致しない証明書も、rdp01.corp.example への接続で通過します。
  • x509_utils_get_dns_names() は GEN_DNS エントリのみ要求します。コードはどこでも iPAddress SAN エントリを読みません。そのため RDP 接続先が IP リテラルのとき、FreeRDP は IP を単なる文字列として CN と DNS SAN エントリと照合します。

2026 年 7 月のアドバイザリ GHSA-43hh-p3vw-hfx3 は 3 つの身元確認の弱点を文書化し、バージョン 3.29.0 が修正したと述べていました。その修正セットが閉じたのは最初のケース(埋め込み NUL による切り詰め)だけです。Common Name と IP リテラルのケースは tag 3.29.0 以降バイト同一のままで、GHSA-jq25-3374-4262 が 2026 年 10 月にこの残存ギャップを文書化しました。

どのように悪用されるか?

  1. 攻撃者は、被害者の RDP 接続を傍受またはリダイレクトする位置を得ます。さらに、クライアントが信頼する CA に連なり、Common Name が接続先のホスト名であるか、DNS SAN に接続先の IP を文字列として含む証明書も必要です。
  2. 被害者の FreeRDP クライアントが接続し、攻撃者の証明書に対して tls_verify_certificate() を実行します。証明書は実際に信頼された CA が発行しているため、連鎖と有効性の確認は通過します。
  3. Common Name 分岐が、SAN エントリが不一致なのに hostname_match = TRUE を設定するか、IP リテラルの接続先が DNS SAN 文字列と一致します。クライアントは証明書をサーバーの身元として受け入れます。
  4. 攻撃者のエンドポイントが RDP セッションを運びます。画面内容、キーストローク、クリップボード、入力注入です(追跡アドバイザリの影響記述による)。

2 つのアドバイザリの再現ノート以上の公開 PoC は存在しません。元のアドバイザリは、隔離された FreeRDP 証明書ストアにインストールしたローカルテスト CA を使い、FreeRDP の TLS ハンドシェイク経路で 3 つのケースすべてを再現しました。追跡レポートは、連鎖検証済みの証明書に対して未変更の tls_verify_certificate() を直接呼び出しており、完全なネットワークハンドシェイクは実行していません。

攻撃はどのように流れるか?

信頼された証明書を持つ中間者が RDP セッションを提供し、独自実装の身元確認が不一致の証明書を受け入れます。

flowchart LR A["中間者が信頼された CA の
証明書を保有"] --> B["被害者が RDP サーバーに
接続"] B --> C["攻撃者の証明書に対して
tls_verify_certificate が実行される"] C --> D["CN は一致、SAN エントリは
不一致:無条件の OR"] D --> E["IP 接続先に対して iPAddress SAN は
一度も読まれない"] E --> F["クライアントが攻撃者の
身元を受け入れる"] F --> G["セッショントラフィック:画面、
キーストローク、クリップボード"]

攻撃者に何ができるか?

攻撃者は RDP セッション全体を傍受します。追跡アドバイザリの影響宣言によれば、画面内容、キーストローク、クリップボード、入力注入です。どちらのアドバイザリもコード実行や直接的な資格情報抽出を主張しておらず、元のアドバイザリはメモリ破損も主張していません。

この攻撃にはまずネットワーク上の位置と信頼された証明書が必要です。クライアントが信頼しない発行者の証明書は、身元照合の前に連鎖チェックで失敗します。この経路とは独立に証明書をピン留めまたは手動検証するクライアントは、記述されたシナリオの外にあります。

なぜ修正は機能するか?

3.32.2 の 2 つのコミットが、これら 2 つのケースの独自実装による照合を置き換えました。コミット 1a23b21c37「do not check common name if there are DNS SAN」は、Common Name の比較を else if の後ろに移動します:

        common_name = freerdp_certificate_get_common_name(cert, &common_name_length);
        dns_names = freerdp_certificate_get_dns_names(cert, &dns_names_count, &dns_names_lengths);
-
-       /* compare against common name */
-
-       if (common_name)
-       {
-           if (tls_match_hostname(common_name, common_name_length, hostname))
-               hostname_match = TRUE;
-       }
-
        /* compare against alternative names */
-
        if (dns_names)
        {
            for (size_t index = 0; index < dns_names_count; index++)
@@
            }
        }
+       /* compare against common name */
+       else if (common_name)
+       {
+           if (tls_match_hostname(common_name, common_name_length, hostname))
+               hostname_match = TRUE;
+       }

Common Name は、証明書が DNS SAN エントリを 1 つも持たないときにのみ参照されるようになりました。これは RFC 6125 の 6.4.4 節の規則です。

コミット 350539ec9a「add IP SAN checks」は iPAddress 抽出の経路を追加します。接続先が IP として解析されるとき、ループはバイナリを考慮した比較で証明書の iPAddress SAN エントリと照合し、DNS 文字列照合には決して後退しません。

この修正は報告された 2 つのケースに対して完全です。2 つのコミットが書き換えたブロックに、プロジェクト内の tls_match_hostname() の呼び出しがすべて含まれています。元のアドバイザリの 3 番目のケース(埋め込み NUL による切り詰め)はすでに 3.29.0 で修正されていました。

新しい IP 経路には欠陥が 1 つ残っていますが、安全側に失敗します。3.32.2 と 3.33.0 では、ヘルパー utils_compare_ip_strings() が inet_pton() の誤った戻り値を判定するため、有効なアドレスをすべて拒否します。そのため IP リテラルの接続先は iPAddress SAN エントリと一致せず、クライアントは known-hosts の確認またはユーザーへの確認に移ります。コミット f5e8a54fb2 が 2026 年 11 月 3 日、3.33.0 のリリース後にこの判定を修正しました。

侵害されたか確認するには?

公開されたインジケーターはなく、アドバイザリは悪用を報告していません。成功した傍受は、クライアントには通常の TLS セッションのように見えます。

クライアントには攻撃の記録が残りません。連鎖が信頼され名前が一致すると、tls_verify_certificate() は FreeRDP の known-hosts ストアを読むことも更新することもなく証明書を受け入れるため、攻撃者の証明書はそこにエントリを残しません。サーバー側の RDP 接続ログのほうが有力な手がかりです。想定外の送信元アドレスからのセッションは確認に値しますが、傍受の証拠ではありません。

年表

  • 2026-07-15:GHSA-43hh-p3vw-hfx3 が公開され、3 つの身元確認の弱点を文書化し、3.29.0 が修正したと述べた。
  • 2026-10-07:残存ケースへの 2 つの修正コミットが Armin Novak によって書かれた。
  • 2026-10-12:FreeRDP 3.32.2 が修正を含めてリリースされた。より広範なハードニングリリースの一部として。
  • 2026-10-19:GHSA-jq25-3374-4262 が公開され、3 つのケースのうち 2 つが 3.29.0 で修正されたことがないと文書化した。
  • 2026-11-03:VulnCheck が CVE-2026-121392 を公開し、CVSS v4.0 で 9.1 Critical と評価した。

3.29.0 の修正を主張したアドバイザリは実際の修正より 84 日早く、CVE レコードはリリースの 22 日後に続いた。
図 1:修正を主張した 7 月のアドバイザリから 11 月の CVE レコードまで。出典:FreeRDP のアドバイザリとリリース、VulnCheck の CVE レコード、2026 年 11 月 4 日確認

アドバイザリは 3.29.0 がこれらのケースを閉じたと述べていました。修正コミットはそのアドバイザリの 84 日後に作成され、それを含むリリースは 89 日後に公開されました。

FAQ

なぜこの脆弱性は Critical と High の両方で評価されているのですか?

2 つの評価は、同じ事実に 2 つの CVSS バージョンを適用した結果です。レコードを公開した CVE 採番機関(CNA)の VulnCheck は、CVSS v4.0 で 9.1 Critical(CVSS:4.0/AV:N/AC:H/AT:P/PR:N/UI:N/VC:H/VI:H/VA:N/SC:N/SI:N/SA:N)と評価しています。VulnCheck と FreeRDP 自身のアドバイザリは、どちらも CVSS v3.1 で 7.4 High(CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:H/I:H/A:N)としています。

この脆弱性は FreeRDP サーバーやプロキシに影響しますか?

脆弱性はクライアント側のサーバー身元確認、tls_verify_certificate() にあります。3.32.2 のリリースノートは同じバッチで他に 44 件のアドバイザリを挙げており、悪意あるクライアントやサーバーのメッセージに対してコードを強化しています。

元のアドバイザリは間違っていたのですか?

修正済みバージョン欄は 3.29.0 としていました。追跡調査は、3.29.0 の修正セットが埋め込み NUL のケースのみを閉じ、他の 2 つのケースがその tag 以降バイト同一だったことを示しました。欄は 3 つの文書化されたケースのうち 2 つについて不正確でした。

誰がこれらの脆弱性を報告したのですか?

元の 3 ケースのアドバイザリは、電子科技大学(UESTC)の Bin Luo(GitHub ユーザー 1121984919)が報告しました(アドバイザリによる)。不完全な修正を文書化した追跡レポートは報告者を明らかにしていません。報告者の指示の下で Claude をツールとして使用し、報告者が提出前に引用されたすべてのコミットと行を再検証したことを開示しています。

3.33.0 への更新でも修正されますか?

はい。修正は 3.32.2 に入り、2026 年 11 月 2 日にリリースされた 3.33.0 がそれを含みます。3.32.2 が最小要件です。

傍受者が来る前に、保有する FreeRDP のコピーを見つける

3.32.2 未満のすべての FreeRDP ビルドが対象範囲で、製品に組み込まれたコピーも含まれます。Ostorlab の SCA と SBOM スキャンは、リポジトリとイメージの依存関係を棚卸しし、どのコンポーネントと製品が対象の FreeRDP を組み込んでいるかを把握させます。

参考文献

  • CVE-2026-121392、両方の CVSS ベクトルを含む VulnCheck の CVE レコード:https://www.cve.org/CVERecord?id=CVE-2026-121392(2026 年 11 月 4 日確認)
  • VulnCheck アドバイザリ、「FreeRDP before 3.32.2 Certificate Identity Validation Bypass via tls_verify_certificate」:https://www.vulncheck.com/advisories/freerdp-before-3.32.2-certificate-identity-validation-bypass-via-tls-verify-certificate(2026 年 11 月 4 日確認)
  • GHSA-jq25-3374-4262、FreeRDP アドバイザリ、「Incomplete fix for GHSA-43hh-p3vw-hfx3」:https://github.com/FreeRDP/FreeRDP/security/advisories/GHSA-jq25-3374-4262(2026 年 11 月 4 日確認)
  • GHSA-43hh-p3vw-hfx3、FreeRDP アドバイザリ、「TLS certificate identity validation accepts malformed and non-authoritative identities」:https://github.com/FreeRDP/FreeRDP/security/advisories/GHSA-43hh-p3vw-hfx3(2026 年 11 月 4 日確認)
  • 修正コミット 1a23b21c37、「[crypto,tls] do not check common name if there are DNS SAN」:https://github.com/FreeRDP/FreeRDP/commit/1a23b21c37(2026 年 11 月 4 日確認)
  • 修正コミット 350539ec9a、「[crypto,tls] add IP SAN checks」:https://github.com/FreeRDP/FreeRDP/commit/350539ec9a(2026 年 11 月 4 日確認)
  • 追跡コミット f5e8a54fb2、「[core,utils] fix return check for inet_pton」:https://github.com/FreeRDP/FreeRDP/commit/f5e8a54fb2(2026 年 11 月 4 日確認)
  • FreeRDP 3.32.2 リリースノート:https://github.com/FreeRDP/FreeRDP/releases/tag/3.32.2(2026 年 11 月 4 日確認)
  • 脆弱なソース、tag 3.32.1 の libfreerdp/crypto/tls.c:https://raw.githubusercontent.com/FreeRDP/FreeRDP/3.32.1/libfreerdp/crypto/tls.c(2026 年 11 月 4 日確認)
  • CISA の Known Exploited Vulnerabilities カタログ、JSON フィード、CVE-2026-121392 で検索:https://www.cisa.gov/sites/default/files/feeds/known_exploited_vulnerabilities.json(2026 年 11 月 4 日確認)