以下查询在我的程序中执行,其中' a'是我作为输入和参考的参数值。在查询中传递它。
select * from emp where name LIKE LOWER('%a%')
有人能告诉我是否可以对上述查询进行SQL注入攻击或是否安全?
我看过SQL注入where子句&喜欢运算符,但我们也可以使用函数调用。我可以通过什么而不是' a'用于SQL注入。
我正在使用PL / SQL编辑器& Oracle DB。
答案 0 :(得分:3)
当您的应用程序与环境(其他程序或用户)交互并使用字符串连接从部件组装SQL查询时,会出现SQL注入的风险。例如,您可以编写PL / SQL过程:
create or replace procedure myproc(a varchar2) is
sql_str varchar2(4000);
sql_result number;
begin
execute immediate 'select count(*) from mytable where mycolumn = ' || a into sql_result;
end;
此程序容易受到攻击。你可以传递一个字符串''abc''' or 1 = 1
或类似的东西,它会扭曲结果(或使事情变得更糟)
或者你可以这样写:
create or replace procedure myproc(a varchar2) is
sql_str varchar2(4000);
sql_result number;
begin
execute immediate 'select count(*) from mytable where mycolumn = :A' using a into sql_result;
end;
这个程序并不容易受到攻击 你也可以写
create or replace procedure myproc(a varchar2) is
sql_str varchar2(4000);
sql_result number;
begin
select count(*)
into sql_result
from mytable
where mycolumn = a;
end;
这根本没有问题,它是最安全的方式(它是"静态SQL"),但有时我们需要动态SQL(如前两个例子)。
为什么第一种方式不好而第二种方式很好?这是因为SQL引擎编译查询几乎像其他编译器一样编译它们的代码,比如C ++。 SQL引擎将查询编译为"程序"并定义了可能的"变量"在这个"程序"。 "变量"在第二个过程中是参数:A
。如果查询包含"变量",引擎会询问它们的值(USING
子句)并将它们传递给已编译的查询。在第一种情况下,引擎获得串联字符串:
select count(*) from mytable where mycolumn = 'abc' or 1 = 1
认为它像一个整体"程序"并执行它"按原样#34;。在第二种情况下,引擎获取字符串
select count(*) from mytable where mycolumn = :A
编译它,定义1"变量" A
并询问它的价值,然后将其传递给"程序"以及该程序"只需在'abc' or 1 = 1
列中搜索值mycolumn
。这不仅适用于PL / SQL代码中的动态SQL。它在任何语言中的工作方式都相同,所有流行的框架(对于java,c#,delphi等)和所有流行的DBMS都提供了安全工作的工具,如第二个例子所示。
当然,它是简化的例子,有时后果可能会更糟糕。
答案 1 :(得分:1)
a可以
1') or 1 = 1 or LIKE LOWER('1
你应该确保通过剥去。
中的斜杠来传递一个干净的值答案 2 :(得分:1)
您几乎可以在任何地方使用SQL注入。 查看我的白皮书,Google" SQL Injection Anywhere"这表明在奇怪的地方注射 - 包括函数调用。