Oracle - Почему EXECUTE IMMEDIATE разрешено в хранимых процедурах? - PullRequest
0 голосов
/ 24 апреля 2018

Почему EXECUTE IMMEDIATE разрешено в хранимых процедурах, если хранимые процедуры предназначены для смягчения атак внедрения SQL?Принятый ответ на следующий вопрос именует их как шаг против таких атак:

Что такое хранимая процедура? https://stackoverflow.com/a/459531/3163495

"Хранимые процедурытакже имеет преимущество в плане безопасности, заключающееся в том, что вы можете предоставлять права на выполнение хранимой процедуры, но пользователю не нужно иметь разрешения на чтение / запись для базовых таблиц. Это хороший первый шаг против внедрения SQL. "

... если хранимая процедура не использует EXECUTE IMMEDIATE.

Этот код PL / SQL возвращает описание продукта (второй параметр).

CREATE OR REPLACE PROCEDURE prodDescr(vname IN VARCHAR2, vresult OUT VARCHAR2) AS
vsql VARCHAR2(4000);
BEGIN
vsql := 'SELECT description FROM products WHERE name=''' || vname || '''';
EXECUTE IMMEDIATE vsql INTO vresult;
END;

Вредоносный ввод пользователя.

A' AND 1=2 UNION SELECT password FROM members WHERE username='admin

Сгенерированный запрос.

SELECT description FROM products WHERE name='A' OR 1=2 UNION SELECT password FROM members WHERE username='admin'

Когда запрос выполняется, злоумышленник получаетпароль администратора.

Как видите, несмотря на то, что мы использовали хранимую процедуру, злоумышленник может использовать уязвимость так же легко, как если бы мы были разработчиком-любителем, объединяющим некоторые операторы SELECT в PHP безУтверждая дезинфицирующий вклад.Мне кажется, может быть очень ошибочным говорить разработчикам, что хранимые процедуры помогут обеспечить безопасность вашей базы данных.

Ответы [ 2 ]

0 голосов
/ 24 апреля 2018

Хранимые процедуры не обеспечивают безопасность вашей базы данных. Это никогда не было правдой.

Никакой язык, структура или API не могут обеспечить безопасность вашей базы данных.

Ответственность за написание безопасного кода лежит на разработчику.

Если вы используете EXECUTE IMMEDIATE небезопасным способом, значит, у вас есть уязвимость.

То же самое верно, когда вы не используете хранимые процедуры - если вы пишете динамический SQL, используя любой язык приложения, вы рискуете создать уязвимости SQL-инъекций.

0 голосов
/ 24 апреля 2018

Execute Immediate все еще можно использовать безопасным способом.Все сводится к логике хранимого процесса.Concat делает код небезопасным, а не немедленным выполнением.

vsql := 'SELECT description FROM products WHERE name=''' || vname || '''';

Следует использовать переменные связывания или вызов dbms_assert.

  vsql := 'select count(1) from all_objects where owner = :1'
  EXECUTE IMMEDIATE vsql into vresult using vname ;

ИЛИ

 vsql := 'select count(1) from all_objects where owner ='||DBMS_ASSERT.ENQUOTE_LITERAL(vname);
  EXECUTE IMMEDIATE vsql into vresult  ;

В полном примере ниже используются оба метода.Первый имеет привязку (и), а второй завернут в DBMS_ASSERT.

SQL>declare
      v_in varchar2(2000);
      ret  varchar2(2000);
    begin
      v_in := 'KLRICE';
     EXECUTE IMMEDIATE 'select count(1) from all_objects where owner = :1' into ret using v_in ;
     dbms_output.put_line('First Object Count  : ' || ret);

     EXECUTE IMMEDIATE 'select count(1) from all_objects where owner ='||DBMS_ASSERT.ENQUOTE_LITERAL(v_in)  into ret ;

    dbms_output.put_line('Second Object Count  : ' || ret);
  end
SQL> /
First Object Count  : 74
Second Object Count  : 74


PL/SQL procedure successfully completed.

SQL> 
...