使用数据库级MD5函数是否比应用程序级函数存在更大的安全风险?

发布于 2024-08-20 00:09:08 字数 433 浏览 9 评论 0原文

我有一段代码可以验证用户的用户名和密码,其内容如下:

$sql = "SELECT * 
FROM user 
WHERE 
    username='{$_POST['username']}' AND 
    password=MD5('{SALT}{$_POST['password']}')";

这比这样做更安全/更不安全吗?

$sql = "SELECT * 
FROM user 
WHERE 
    username='{$_POST['username']}' AND 
    password='".md5(SALT.$_POST['password'])."'";

无论在何处/是否进行转义,第一种方法是否容易受到 SQL 注入攻击?对于除 MySQL 之外的其他数据库引擎,答案是否相同?

I've got a chunk of code that validates a user's username and password, which goes something like this:

$sql = "SELECT * 
FROM user 
WHERE 
    username='{$_POST['username']}' AND 
    password=MD5('{SALT}{$_POST['password']}')";

Is this any more/less secure than doing it like this?

$sql = "SELECT * 
FROM user 
WHERE 
    username='{$_POST['username']}' AND 
    password='".md5(SALT.$_POST['password'])."'";

Regardless of where/if escaping is done, is the first method vulnerable to sql injection attacks? Would the answer be the same for other database engines besides MySQL?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

极度宠爱 2024-08-27 00:09:08

您应该使用准备好的语句看看这个问题

You should use prepared statements instead and have a look at this question.

此刻的回忆 2024-08-27 00:09:08

说到注入,如果你正确地转义变量,两种方法都是安全的。

如果您使用完整的查询日志记录,第一种情况将更容易受到攻击,因此密码将显示为纯文本。

此外,如果您的系统受到某种充当脚本和数据库之间代理的病毒的影响,它就能够捕获您的密码。

您可能遇到的最后一个问题(事实上,很少见)是当系统感染病毒时,病毒会从内存中读取敏感数据。

我希望这是有道理的。

Speaking about injection, both ways are secure, if you properly escape variables.

The first case will be more vulnerable, if you use complete query logging, and so the password will appear as plain text.

Besides, if your system is affected by some virus that works as proxy between your script and database, it'll be able to catch your password.

One last problem that you may encounter (quite rarely, in fact), is when the system is inflicted with a virus, that reads sensible data from memory.

I hope this makes sense.

泛泛之交 2024-08-27 00:09:08

天啊,请告诉我你正在做某种类型的 mysql_escape_stringmysql_real_escape_string 或至少 addslashesaddcslashes在将任何 $_POST 变量插入原始 MySQL 语句之前

我认为最安全的方法是:

a) 使用 filter_varpreg_replace 删除 $_POST['username'] 中的无关字符

b) < code>SELECT 来自 MySQL 的用户名行(同时获取摘要密码)

c) 将 $_POST 中的密码消息摘要版本与检索到的行的消息摘要版本进行比较(假设你不会在应用程序代码中留下你的密码(明文),而不是在 SQL 语句中

如果你这样做,那么只有 1 个可能的注入位置(用户名),并且当你执行 时这是几乎不可能的preg_replace( '/\W/', '', $_POST['username'] ) 删除任何非 A-Za-z0-9_- 的内容(或更改为您的用户名白名单字符)。

然而,如果你进行了绝对正确的消毒,那么在哪里进行比较并不重要。不过,从理论上讲,我会允许与用户输入和原始 SQL 语句进行尽可能少的交互(即仅通过用户名进行 SELECT 并在数据库外部进行比较)。

Oh god, please tell me you're doing some type of mysql_escape_string or mysql_real_escape_string or AT LEAST addslashes or addcslashes to any $_POST variables before you insert them into a raw MySQL statement?

I think the most secure way to do this is to:

a) use filter_var or preg_replace to get rid of extraneous characters from the $_POST['username']

b) SELECT the row by the username from MySQL (also grabbing the digested password)

c) compare the message digested version of the password from the $_POST to that of the retrieved row (assuming you don't leave your password cleartext) in your application code, not in the SQL statement

If you do it this way, there's only 1 possible place for injection (username), and it's pretty impossible when you're doing a preg_replace( '/\W/', '', $_POST['username'] ) which removes anything not A-Za-z0-9_- (or change to your username whitelist of characters).

However, if you're doing rock-solid proper sanitization, it really doesn't matter where you do your comparison. Theoretically, though, I'd allow for the least possible interaction with user input and raw SQL statements (i.e. only SELECTing by username and comparing outside of your DB).

人生戏 2024-08-27 00:09:08

首先使用 MD5 是为了避免成为不安全的算法,并且永远不应该将其用于密码。您应该使用陈旧的 sha256,并且大多数数据库没有此函数调用。但即使数据库有,我也认为这是一个坏主意。这不是一个坏主意,但最好保留尽可能少的密码副本。通常,数据库可能位于完全不同的计算机上,如果该计算机受到威胁,则攻击者可以通过查看查询来获取明文密码。就 SQL 注入而言,安全性没有区别,从您的查询来看,您应该更担心 SQL 注入。

To start off with MD5 is prevent to be an insecure algorithm and should never be used for passwords. You should use a staled sha256 and most databases do not have this function call. But even if the database did I think its a bad idea. Not a very bad idea, but its best to keep as few copies of your password around. Often the database can be on a completely different machine, and if that machine where compromised then the attacker could obtain clear text passwords by looking at the quires. In terms of SQL Injection, there is no difference in security and judging by your queries you should be more worried about SQL injection.

债姬 2024-08-27 00:09:08

无论在何处/是否进行转义,第一种方法是否容易受到 SQL 注入攻击?

如果进行适当的转义和清理,则不会发生 SQL 注入

除了 MySQL 之外,其他数据库引擎的答案是否相同?

我认为你应该更多地关注执行一项行动而不是另一项行动所花费的费用。在其他条件相同的情况下,第一种方法的执行时间比第二种方法要少。

Regardless of where/if escaping is done, is the first method vulnerable to sql injection attacks?

SQL injection will not occur if proper escaping and sanitizing takes place

Would the answer be the same for other database engines besides MySQL?

I think you should look more at the expense taken to perform one action over another. The first method would take less time to execute than the second method, ceteris paribus.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文