PHP重大脆弱性は何が危険? php2shellについて図でわかりやすく解説

執筆・制作:何でも自作する人(運営者について)

PHP / PHP2Shell / 脆弱性 / セキュリティ


PHPの脆弱性「PHP2Shell」がニュースになっています。2026年10月21日にPHPが修正版を公開した、PHP本体の脆弱性2件の通称です。

どちらも深刻度はCVSS v4で9.2(Critical)です。条件がそろうと、ログインなしで外からサーバー上のコマンドを実行される、つまりサーバーを乗っ取られるおそれがあります。

発見者には、Wiz Researchの研究者らに加えて、OpenAIの脆弱性発見AI「Codex Security」のチームも名を連ねています。

騒ぎが大きいのは、問題がPHPそのものにあるからです。WordPressやDrupalのようなアプリのコードに関係なく、古いPHPで動いていれば影響を受ける可能性があります。発見者によると、PHP 5.4以降のほぼすべてのバージョンが、2件のどちらかに当てはまります。セキュリティ企業Datadogの解説では、AWSが公開前の10月17日から悪用の試みを確認していたとされています。

以下、2件を「618」「619」と呼びます。

ざっくり言うと:台帳と棚がズレる

サーバーの中を、棚(メモリ)と台帳(どの棚に何があるかの記録)がある作業場だと考えてください。

通常の流れ(3ステップ)

  1. 準備:台帳に「通常の命令は棚1」と書き、棚1に通常の命令を入れる
  2. 使う:担当者が台帳を見て棚1を開け、命令を実行する
  3. 片付け:使い終わったら棚1を空け、台帳の記録も消す

どこでズレるか

どちらの場合も、後で棚1を開ける担当者(618では後片付け担当、619では次に使う担当者)は、いつもどおり台帳を信じるだけです。中身がすり替わっていても気づけず、攻撃命令を実行してしまいます。

図で見る:通常の流れ

1. 準備:台帳に「通常の命令は棚1」と書き、棚1に通常の命令を入れる。2. 使う:担当者が台帳を見て棚1を開け、命令を実行する。3. 片付け:使い終わったら棚1を空け、台帳の記録も消す。

担当者は棚の中身を確かめません。台帳を信じて開けるだけです。台帳と中身が一致している限り、それで問題は起きません。

図で見る:618は①準備の途中で止まる

前提:攻撃者が攻撃命令と、後の処理でメモリを大量に使わせるためのデータを送り、使い終わった棚1に攻撃命令の紙が残る。1. 準備:受け取ったデータを1件ずつ台帳に書き足す途中、台帳に「通常の命令は棚1」と先に書いたところでメモリの上限に達し、中身を書き直す前に止まる。2. 使う:止まったので来ない。3. 後片付け:止まった後も後片付けは動き、後片付け担当が台帳を信じて棚1を開け、攻撃命令を通常の命令として処理する。

攻撃者は、フォームの送信に見せかけて「攻撃命令」と「大量データ」を一緒に送ります。大量データは、後の処理でメモリを大量に使わせるためのデータです。サーバーはこれをデータとして受け取るだけです。攻撃命令を置いた棚1は、使い終わると空き扱いになりますが、紙は入ったままです。

PHPには、1回のアクセスで使えるメモリの上限があります(設定名は memory_limit。128MBなどが一般的です)。サーバーは受け取ったデータを1件ずつ台帳に書き足していき、そのたびにメモリを少しずつ使います。

1件を書き足す手順は、台帳に「1件増えた(中身は棚1)」と先に書き、それから棚1の中身を書くという順番になっていました。中身を書くには、項目名を書くための用紙(メモリ)がもう少し必要です。

攻撃者は大量データの量を調整して、ちょうどこの「台帳に書いた直後、用紙を取る瞬間」にメモリの上限を超えるようにします。上限を超えたところで準備は中断され、棚1の中身は書き直されないまま残ります。

台帳は「通常の命令」、中身は攻撃命令のまま。準備の途中で止まったので、②使うには進みません。それでも、止まった後の後片付けだけは必ず動きます。後片付け担当が台帳を見て棚1を開け、攻撃命令を通常の命令として処理してしまいます。

つまり、大量データの役割は、メモリを上限ぎりぎりまで使わせて、中身を書く直前で止めさせることです。

図で見る:619は③片付けで台帳が残る

前の回の3. 片付け:棚1は空けたのに、台帳の「通常の命令は棚1」という記録が残る。次の回の1. 準備:攻撃者のデータが届き、受付が空いた棚1に保管する。次の回の2. 使う:担当者は台帳を信じて棚1を開け、攻撃命令を実行する。

619は、2回分のアクセスにまたがる話です。まず前の回の③片付けで、棚1は空けたのに台帳の記録を消し忘れます。

次の回の①準備で、攻撃者のデータが届きます。受付は空いている棚1にそれを保管するだけで、この時点ではまだ何も起きません。

ところが次の回の②使うで担当者が台帳を見ると、「通常の命令は棚1」と書いてあります。棚1を開けると確かに紙が入っているので、それを通常の命令だと思って実行してしまいます。

実際のPHPでは

棚はメモリ、台帳は「どこに何があるか」を指すPHP内部の記録です。攻撃者が送るのは文章の命令ではなく、メモリに残る細工したデータです。それが内部の記録をたどって読まれると、次に呼ぶ処理の行き先などとして使われ、最終的にコマンドの実行までつながります。

どちらも、メモリ上のデータの配置やサーバーの構成といった成立条件があり、大量データを送れば必ず成功するわけではありません。それでも公開前から悪用の試みが報告されているので、条件を見積もるより先に更新するのが安全です。

対策:修正版に更新する

2026年10月22日時点で、修正版は次のとおりです。

系列修正版
PHP 8.28.2.35 以降
PHP 8.38.3.36 以降
PHP 8.48.4.27 以降
PHP 8.58.5.12 以降

PHP公式は、修正版への更新だけが確実な対策だとしています。設定による緩和策(619の session.upload_progress.enabled=0 など)もありますが、影響を減らすだけです。

Apacheのモジュール、PHP-FPM、FrankenPHPなど、HTTPを受けるPHPはすべて対象です。コンテナや、PHPを同梱しているアプリの中のPHPも忘れずに確認してください。

出典