LFI2RCE via Eternal waiting
Reading time: 11 minutes
tip
AWSハッキングを学び、実践する:HackTricks Training AWS Red Team Expert (ARTE)
GCPハッキングを学び、実践する:HackTricks Training GCP Red Team Expert (GRTE)
Azureハッキングを学び、実践する:
HackTricks Training Azure Red Team Expert (AzRTE)
HackTricksをサポートする
- サブスクリプションプランを確認してください!
- **💬 Discordグループまたはテレグラムグループに参加するか、Twitter 🐦 @hacktricks_liveをフォローしてください。
- HackTricksおよびHackTricks CloudのGitHubリポジトリにPRを提出してハッキングトリックを共有してください。
基本情報
デフォルトでは、ファイルがPHPにアップロードされると(期待されていなくても)、**php[a-zA-Z0-9]{6}
**のような名前の一時ファイルが/tmp
に生成されますが、数字を含まない生成ファイルがあるDockerイメージも見たことがあります。
ローカルファイルインクルージョンでは、アップロードされたファイルをインクルードできれば、RCEを得ることができます。
デフォルトでは、PHPは単一のリクエストで20ファイルのアップロードのみを許可します(/etc/php/<version>/apache2/php.ini
で設定されています):
; Maximum number of files that can be uploaded via a single request
max_file_uploads = 20
また、潜在的なファイル名の数は 62*62*62*62*62*62 = 56800235584 です。
その他の技術
その他の技術は、PHPプロトコルを攻撃することに依存しています(パスの最後の部分だけを制御している場合はできません)、ファイルのパスを開示すること、期待されるファイルを悪用すること、またはPHPにセグメンテーションフォルトを引き起こさせてアップロードされた一時ファイルが削除されないようにすることです。
この技術は最後のものと非常に似ていますが、ゼロデイを見つける必要はありません。
永遠の待機技術
この技術では相対パスを制御する必要があるだけです。ファイルをアップロードし、LFIが決して終わらないようにすることができれば、アップロードされたファイルをブルートフォースして見つけるための「十分な時間」を得ることができます。
この技術の利点:
- インクルード内の相対パスを制御するだけで済む
- nginxやログファイルへの予期しないアクセスレベルを必要としない
- セグメンテーションフォルトを引き起こすためにゼロデイを必要としない
- パスの開示を必要としない
この技術の主な問題は次のとおりです:
- 特定のファイルが存在する必要がある(他にもあるかもしれません)
- 潜在的なファイル名の「狂った」数: 56800235584
- サーバーが数字を使用していない場合、総潜在数は: 19770609664
- デフォルトでは1回のリクエストで20ファイルしかアップロードできません。
- 使用されているサーバーの最大並列ワーカー数。
- この制限と前述の制限により、この攻撃が長引く可能性があります
- PHPリクエストのタイムアウト。理想的にはこれは永遠であるべきか、アップロードされた一時ファイルを削除せずにPHPプロセスを終了させるべきです。そうでなければ、これもまた厄介です。
では、どうやってPHPインクルードを決して終わらせることができるのでしょうか?ファイル**/sys/kernel/security/apparmor/revision
**をインクルードするだけです(残念ながらDockerコンテナでは利用できません...)。
試してみてください:
php -a # open php cli
include("/sys/kernel/security/apparmor/revision");
Apache2
デフォルトでは、Apacheは150の同時接続をサポートしています。 https://ubiq.co/tech-blog/increase-max-connections-apache/ に従って、この数を最大8000まで増やすことが可能です。このモジュールでPHPを使用するには、次の手順に従ってください: https://www.digitalocean.com/community/tutorials/how-to-configure-apache-http-with-mpm-event-and-php-fpm-on-ubuntu-18-04。
デフォルトでは、(私のテストで確認したところ)PHPプロセスは永遠に続くことができます。
数学をしてみましょう:
- 149の接続を使用して、149 * 20 = 2980の一時ファイルを生成できます。
- 次に、最後の接続を使用してブルートフォースを行います。
- 10リクエスト/秒の速度で、時間は次の通りです:
- 56800235584 / 2980 / 10 / 3600 ~= 530時間(265時間で50%の確率)
- (数字なし)19770609664 / 2980 / 10 / 3600 ~= 185時間(93時間で50%の確率)
warning
前の例では、他のクライアントを完全にDoSしています!
Apacheサーバーが改善され、4000の接続を悪用できる場合(最大数の半分)、3999*20 = 79980
ファイルを作成でき、時間は約19.7時間または6.9時間(10時間、3.5時間で50%の確率)に短縮されます。
PHP-FMP
通常のphpモジュールを使用してApacheでPHPスクリプトを実行する代わりに、ウェブページが PHP-FMPを使用している場合(これによりウェブページの効率が向上するため、一般的に見られます)、技術を改善するために他にできることがあります。
PHP-FMPは、/etc/php/<php-version>/fpm/pool.d/www.conf
でパラメータ request_terminate_timeout
を設定することを許可します。
このパラメータは、PHPへのリクエストが終了する最大秒数を示します(デフォルトでは無限ですが、パラメータがコメント解除されると30秒)。リクエストがPHPによって処理されている間、指定された秒数が経過すると、終了します。これは、リクエストが一時ファイルをアップロードしている場合、PHP処理が停止したため、それらのファイルは削除されないことを意味します。したがって、その時間リクエストを持続させることができれば、削除されない数千の一時ファイルを生成でき、これによりそれらを見つけるプロセスが加速され、すべての接続を消費することによるプラットフォームへのDoSの確率が減少します。
したがって、DoSを回避するために、攻撃者が同時に100の接続のみを使用すると仮定し、php-fmpによるPHPの最大処理時間(request_terminate_timeout
)が30秒**であるとします。したがって、秒あたり生成できる一時ファイルの数は100*20/30 = 66.67
です。
次に、10000ファイルを生成するには、攻撃者は**10000/66.67 = 150秒
が必要です(100000ファイルを生成するには、時間は25分**になります)。
その後、攻撃者はこれらの100接続を使用してブルートフォース検索を行うことができます。300 req/sの速度を仮定すると、これを悪用するのに必要な時間は次の通りです:
- 56800235584 / 10000 / 300 / 3600 ~= 5.25時間(2.63時間で50%の確率)
- (100000ファイルの場合)56800235584 / 100000 / 300 / 3600 ~= 0.525時間(0.263時間で50%の確率)
はい、EC2の中サイズインスタンスで100000の一時ファイルを生成することは可能です:
.png)
warning
タイムアウトをトリガーするには、脆弱なLFIページを含めるだけで十分です。そうすれば、永遠のインクルードループに入ります。
Nginx
デフォルトでは、Nginxは同時に512の並列接続をサポートしているようです(この数は改善可能です)。
tip
AWSハッキングを学び、実践する:HackTricks Training AWS Red Team Expert (ARTE)
GCPハッキングを学び、実践する:HackTricks Training GCP Red Team Expert (GRTE)
Azureハッキングを学び、実践する:
HackTricks Training Azure Red Team Expert (AzRTE)
HackTricksをサポートする
- サブスクリプションプランを確認してください!
- **💬 Discordグループまたはテレグラムグループに参加するか、Twitter 🐦 @hacktricks_liveをフォローしてください。
- HackTricksおよびHackTricks CloudのGitHubリポジトリにPRを提出してハッキングトリックを共有してください。