このPHPコードはどれほど危険ですか?
-
03-07-2019 - |
質問
このphpコードはどれほど危険ですか?それについて何ができますか?
$name = $_POST["user"];
$pwd = $_POST["pwd"];
$query = "SELECT name,pwd FROM users WHERE name = '$name' AND pwd = '$pwd'";
解決
起こりうる問題:
- SQLインジェクション
- XSSインジェクション(このコードが挿入クエリである場合、それは明確な問題になります)
- プレーンテキストパスワード
SQLステートメントに問題がある可能性があります。 SQLインジェクションのために自分を開いたままにしておくのは悪い習慣です。
SQLインジェクションが悪い。私を信じて。
HTMLページに$ userを表示する場合、人々が<!> quot; hack <!> quot;する機能を含めたくない場合があります。
などのコマンドを入力してレイアウトを作成します<H1>HI MOM</H1>
または javascript の束。
また、パスワードをプレーンテキストで保存しないでください(cagcowboyをキャッチしてください!)。データベースを管理(またはハッキング)する人々に力を与えすぎます。誰かのパスワードを知る必要はありません。
次のような戦術を試してください:
// mostly pulled from http://snippets.dzone.com/posts/show/2738
function MakeSafe($unsafestring)
{
$unsafestring= htmlentities($unsafestring, ENT_QUOTES);
if (get_magic_quotes_gpc())
{
$unsafestring= stripslashes($unsafestring);
}
$unsafestring= mysql_real_escape_string(trim($unsafestring));
$unsafestring= strip_tags($unsafestring);
$unsafestring= str_replace("\r\n", "", $unsafestring);
return $unsafestring;
}
// Call a function to make sure the variables you are
// pulling in are not able to inject sql into your
// sql statement causing massive doom and destruction.
$name = MakeSafe( $_POST["user"] );
$pwd = MakeSafe( $_POST["pwd"] );
// As suggested by cagcowboy:
// You should NEVER store passwords decrypted.
// Ever.
// sha1 creates a hash of your password
// pack helps to shrink your hash
// base64_encode turns it into base64
$pwd = base64_encode(pack("H*",sha1($pwd)))
他のヒント
これは危険です。
SQLインジェクションは別として、パスワードがプレーンテキストで保存されているように見えますが、これは良くありません。
$ queryをSQLデータベースに渡さない場合、そのコードは非常に安全です。
名前の0';drop table users;--
を投稿する場合
コマンドは最終的には
になりますselect name, pwd form users where name='0';
drop table users; --'and pwd = '[VALUE OF PWD]'
つまり、最初にデータを取得し、次にユーザーテーブルを強制終了し、コメントなので残りの部分は何もしません。
PHPの特定のmysqlコマンドは、sqlが渡されると複数のクエリを実行します。これを回避する最良の方法は、パラメータ化されたクエリです。
すべてのDBアクセスにPDOを使用していますが、強くお勧めします。頭上にリンクはありませんが、使用したチュートリアルはGoogleを突破しました。
SQLインジェクションが発生しやすいだけでなく、インジェクションが意図されていない場合にも失敗します。
たとえば、ユーザーは<!> quot; Guillaume Fran <!>#231; ois Antoine、Marquis de L <!>#8217; Hospital <!> quot;という名前を望んでいます。ユーザー名に引用符が含まれており、引用符をエスケープしていないため、クエリは失敗しますが、ユーザーはシステムを壊したくありませんでした!
PDO を使用するか、次のように実行します。
$query = sprintf(
"SELECT 1 FROM users WHERE name = '%s' AND password = '%s'",
mysql_real_escape_string($_POST['name']),
mysql_real_escape_string(md5($_POST['password']))
);
信じられないかもしれませんが、これは安全です... magic_quotes_gpc
がオンになっている場合。 PHP6にはないので、それより前に修正することをお勧めします。
-
$_POST['user'] = "' or 1=1; --";
誰でもアプリにすぐにアクセスできます -
$_POST['user'] = "'; DROP TABLE user; --";
(有料?)ユーザーリストに別れを告げる -
後で出力に$ nameをエコーすると、XSSインジェクション攻撃が発生する可能性があります
:O絶対にやらないで、 これにより、SQLInjection攻撃が発生する可能性があります。たとえば、ユーザーが何らかの方法で入力した場合: 'テーブルユーザーのドロップ- $ usernameの入力として;このコードは元のコードに連結し、テーブルを削除します。ハッカーはさらに多くのことができ、ウェブサイトをハッキングできます。
これは通常非常に危険です。場合によっては、データベースのアクセス許可によって軽減される可能性があります。
入力($ nameおよび$ pwd)を検証しません。ユーザーは、これらのフィールドの一方または両方でSQLを送信できます。 SQLはデータベース内の他のデータを削除または変更する可能性があります。
非常に危険です。パスワードの良いアイデアは、パスワードをMD5ハッシュに変換し、それをユーザーの「パスワード」として保存することです。
1)ユーザーがパスワードを盗まれるのを防ぎます
2)ユーザーが悪意のある文字列を書き込んだ場合、エントリ/テーブル/データベースが消去される可能性があります
また、A-Za-z0-9およびおそらくいくつかのアクセント付き文字(特殊文字、*、<!> lt; ' 、<!> gt;は特に)。
ユーザーデータがSQLクエリに含まれる場合、常に mysql_real_escape_string
でデータをサナタイズします。
さらに、パスワード自体ではなく、パスワードのソルトハッシュのみを保存する必要があります。次の関数を使用して、ランダムなソルト値でソルトハッシュを生成および確認できます。
function saltedHash($data, $hash=null)
{
if (is_null($hash)) {
$salt = substr(md5(uniqid(rand())), 0, 8);
} else {
$salt = substr($hash, 0, 8);
}
$h = $salt.md5($salt.$data);
if (!is_null($hash)) {
return $h === $hash;
}
return $h;
}
すべて一緒:
$query = 'SELECT pwd FROM users WHERE name = "'.mysql_real_escape_string($_POST['user']).'"';
$res = mysql_query($query);
if (mysql_num_rows($res)) {
$row = mysql_fetch_assoc($res);
if (saltedHash($_POST["pwd"], $row['pwd'])) {
// authentic
} else {
// incorrect password
}
} else {
// incorrect username
}
それは安全ではありません。PDOのようなものを調べたいかもしれません。 PHP PDO