问题
我们需要在我们的java应用程序中防御'WAITFOR DELAY'sql注入攻击。
背景
[这很长。跳到'解决方案?'以下部分,如果你匆忙]
我们的应用程序主要使用预准备语句和可调用语句(存储过程)来访问数据库。
在一些地方,我们动态构建并执行查询以供选择。在此范例中,我们使用条件对象根据用户输入条件构建查询。例如,如果用户为first_name和last_name指定了值,则结果查询始终如下所示:
SELECT first_name,last_name FROM MEMBER WHERE first_name ='joe' AND last_name='frazier'
(在这个例子中,用户会指定“joe”和“frazier”作为他/她的输入值。如果用户有更多或更少的批评,我们会有更长或更短的查询。我们发现这种方法更容易而不是使用准备好的语句,比存储过程更快/更高效。)
攻击
漏洞审计报告了sql注入失败。攻击者为'last_name'参数注入'frazier WAITFOR DELAY '00:00:20'值,产生了这个sql:
SELECT first_name,last_name FROM MEMBER WHERE first_name ='joe' AND last_name='frazier' WAITFOR DELAY '00:00:20'
结果:查询成功执行,但需要20秒才能执行。攻击者可以占用数据库池中的所有数据库连接,并有效地关闭您的站点。
有关此“等待延迟”攻击的一些观察
我原以为是因为我们使用了Statement executeQuery(String),所以我们可以安全地从sql注入。 executeQuery(String)不会执行DML或DDL(删除或删除)。并且在分号上执行Query(String)choke,因此'Bobby Tables'范例将失败(即用户输入'frazier; DROP TABLE成员'作为参数。参见。http://xkcd.com/327/)
'WAITFOR'攻击在一个重要方面有所不同:WAITFOR修改现有的'SELECT'命令,而不是单独的命令。
攻击仅适用于生成的查询中的“最后一个参数”。即'WAITFOR'必须出现在sql语句的最后
解决方案,廉价黑客还是两者兼而有之?
最明显的解决方案是简单地将“AND 1 = 1”添加到where子句中。
生成的sql立即失败并阻止攻击者:
SELECT first_name,last_name FROM MEMBER WHERE first_name ='joe' AND last_name='frazier' WAITFOR DELAY '00:00:20' AND 1=1
问题
答案 0 :(得分:22)
处理SQL注入的正确方法是使用参数化查询。其他一切都只是在风中撒尿。它可能会工作一次,甚至两次,但最终你会被那种温暖的感觉所打击,说“你搞砸了,严重!”
除了参数化查询之外,您所做的任何事情都将是次优的,并且由您来确保您的解决方案没有其他需要修补的漏洞。
另一方面,参数化查询开箱即用,可以防止所有这些攻击。
答案 1 :(得分:11)
SQL注入是SQL注入 - WAITFOR DELAY
没有什么特别的。
在这个时代,没有理由不在这样简单的查询中使用预准备语句。
(编辑:好的,不是“绝对” - 但几乎从不借口)
答案 2 :(得分:3)
我认为你自己提出了解决方案:参数化查询。
您是如何发现动态构建的查询比使用存储过程更快的?一般情况下,情况往往相反。
答案 3 :(得分:2)
回答你的所有问题:
这是WAITFOR攻击的可行解决方案吗?
没有。只需添加 - 攻击字符串,它将忽略您的修复。
它是否能抵御其他类似的漏洞?
没有。见上文。
我认为最好的选择是使用准备好的陈述。更多的工作,但不那么脆弱。
是。您自己不修复SQL注入。您可以使用已存在的内容并将其正确使用,即通过参数化查询的任何动态部分。
另一个较小的解决方案是转义将在您的查询中插入的任何字符串,但是,将忘记一天而您只需要一个就会受到攻击。
答案 4 :(得分:0)
其他人已经钉了这个(参数化!),但只是触及了几点:
- 这是WAITFOR攻击的可行解决方案吗?
- 它是否可以抵御其他类似的漏洞?
不,它没有。 WAITFOR技巧很可能只是用于“嗅探”漏洞;一旦他们找到了易受攻击的页面,他们就可以在没有DDL或(非SELECT部分)DML的情况下做更多事情。例如,考虑他们是否将以下内容作为last_name
传递' UNION ALL SELECT username, password FROM adminusers WHERE 'A'='A
即使你添加了AND 1 = 1,你仍然会被哄骗。在大多数数据库中,只有SELECT访问才能执行许多恶意操作......
答案 5 :(得分:-4)
如何关注xkcd并清理输入。您可以检查一般的保留字,特别是WAITFOR。