ホームページ  >  記事  >  バックエンド開発  >  PHP セキュリティ - ブルート フォース攻撃

PHP セキュリティ - ブルート フォース攻撃

黄舟
黄舟オリジナル
2017-02-20 09:52:092245ブラウズ



暴力的攻撃

ブルートフォースアタックとは、特別な手段を使わずにあらゆる可能性を尽くした攻撃手法です。より正式な名前は徹底的な攻撃、つまりすべての可能性を使い果たす攻撃です。

アクセス制御の場合、一般的なブルート フォース攻撃では、攻撃者がシステムへのログインを多数回試行します。ほとんどの場合、ユーザー名はわかっており、パスワードは推測するだけで済みます。

ブルートフォース攻撃にはスキルがありませんが、辞書攻撃にはある程度のスキルがあるようです。最大の違いは、推測する際の知性です。辞書攻撃は、ブルート フォース攻撃のように考えられるすべての状況を網羅するのではなく、最も可能性の高い状況のリストを網羅するだけです。

検証の試行を防止したり、許可されるエラーの数を制限したりすることは比較的効果的なセキュリティ対策ですが、その際のジレンマは、正規のユーザーに影響を与えずに攻撃者を特定してブロックする方法です。

この場合、一貫性を判断すると、この 2 つを区別するのに役立ちます。この方法は、第 4 章で説明したセッション ハイジャックを防止する方法とよく似ていますが、正規のユーザーではなく攻撃者を特定する必要がある点が異なります。

次の HTML フォームを考えてみましょう:

CODE:
 
  <form action="http://example.org/login.php"
method="POST">
  <p>Username: <input type="text"
name="username" /></p>
  <p>Password: <input type="password"
name="password" /></p>
  <p><input type="submit"
/></p>
  </form>


攻撃者はこのフォームを表示し、正規のデータを http://www.php.cn/ に POST するスクリプトを作成します:

CODE:
 
 <?php
 
  $username = &#39;victim&#39;;
  $password = &#39;guess&#39;;
 
  $content =
"username=$username&password=$password";
  $content_length = strlen($content);
 
  $http_request = &#39;&#39;;
  $http_response = &#39;&#39;;
 
  $http_request .= "POST /login.php
HTTP/1.1\r\n";
  $http_request .= "Host: example.org\r\n";
  $http_request .= "Content-Type:
application/x-www-form-urlencoded\r\n";
  $http_request .= "Content-Length:
$content_length\r\n";
  $http_request .= "Connection: close\r\n";
  $http_request .= "\r\n";
  $http_request .= $content;
 
  if ($handle = fsockopen(&#39;example.org&#39;, 80))
  {
    fputs($handle, $http_request);
 
    while (!feof($handle))
    {
      $http_response .= fgets($handle, 1024);
    }
 
    fclose($handle);
 
    /* Check Response */
  }
  else
  {
    /* Error */
  }
 
  ?>


このスクリプトを使用すると、攻撃者は単にループを追加して、異なるパスワードの試行を継続し、試行のたびに $http_response 変数をチェックすることもできます。 $http_response 変数が変更されると、正しいパスワードが推測されたと考えることができます。

この種の攻撃を防ぐために講じられるセキュリティ対策は数多くあります。ブルート フォース攻撃では、すべての HTTP リクエストがパスワードを除いてまったく同じであることに気付きました。パスワードは非常に重要です。

一定回数の試行が失敗した後にアカウントを一時的に凍結することは効果的な防御策ですが、攻撃者が正当なユーザーのアプリケーションへのアクセスに影響を与えないようにするために、アカウントを凍結するためのより決定的なアプローチを検討することもできます。

ブルート フォース攻撃をより困難にし、成功する可能性を低くするプロセスもあります。これは、単純な封じ込めメカニズムで効果的に行うことができます。

CODE:
 
 <?php
 
  /* mysql_connect() */
  /* mysql_select_db() */
 
  $clean = array();
  $mysql = array();
 
  $now = time();
  $max = $now - 15;
 
  $salt = &#39;SHIFLETT&#39;;
 
  if (ctype_alnum($_POST[&#39;username&#39;]))
  {
    $clean[&#39;username&#39;] = $_POST[&#39;username&#39;];
  }
  else
  {
    /* ... */
  }
  $clean[&#39;password&#39;] = md5($salt .
md5($_POST[&#39;password&#39;] . $salt));
  $mysql[&#39;username&#39;] =
mysql_real_escape_string($clean[&#39;username&#39;]);
 
  $sql = "SELECT last_failure, password
          FROM   users
          WHERE  username =
&#39;{$mysql[&#39;username&#39;]}&#39;";
 
  if ($result = mysql_query($sql))
  {
    if (mysql_num_rows($result))
    {
      $record = mysql_fetch_assoc($result);
 
      if ($record[&#39;last_failure&#39;]> $max)
      {
        /* Less than 15 seconds since last failure
*/
      }
      elseif ($record[&#39;password&#39;] ==
$clean[&#39;password&#39;])
      {
        /* Successful Login */
      }
      else
      {
        /* Failed Login */
 
        $sql = "UPDATE users
                SET    last_failure = &#39;$now&#39;
                WHERE  username =
&#39;{$mysql[&#39;username&#39;]}&#39;";
 
        mysql_query($sql);
      }
    }
    else
    {
      /* Invalid Username */
    }
  }
  else
  {
    /* Error */
  }
 
  ?>


上記の例では、最後に認証が失敗した後、同じユーザーによる再試行の頻度が制限されます。失敗してから 15 秒以内に再試行すると、パスワードが正しいかどうかに関係なく、検証は失敗します。これがこの計画のキーポイントです。ただし、試行失敗後に 15 秒間アクセスをブロックするだけでは十分ではありません。この時点では、入力が何であっても出力は一貫しており、ログインが成功した場合にのみ出力が異なります。そうしないと、攻撃者は単に一貫性のない出力を調べて、ログインが成功したかどうかを判断する可能性があります。

上記は PHP セキュリティ - ブルート フォース アタックの内容です。その他の関連コンテンツについては、PHP 中国語 Web サイト (www.php.cn) にご注意ください。


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