Parsování dotazu - SQL injection

opio

Parsování dotazu - SQL injection
« kdy: 08. 01. 2016, 10:55:43 »
Ahoj,
mame jeden starsi IS napsany v PHP/mySQL, kde se nepouziva mysql_real_escape_string ani prepared statements na ochranu proti SQL injections. Ted bychom ji potrebovali doplnit. Prepisovat to nikdo nebude, takze musime upravit metodu pres kterou jdou vsechny dotazy exec($query), tedy uvnitr parsovat SQL dotaz a zabezpecit.

zkousel sem parsovat, funguje dobre, ale na dobre napsane dotazy.. selhava to prave pri dotazu, kde by se nekdo snazil ukoncit retezec/dotaz a psat vlastni podminky nebo dotaz druhy

validatorem dotazu bych zabezpecil ukonceni dotazu, ale zmenu podminky ve WHERE uz neodchytim

Nemate s tim zkusenosti nebo nevite o nejakem reseni? Diky
« Poslední změna: 08. 01. 2016, 14:06:18 od Petr Krčmář »


Ado

Re:parsovani dotazu - sql injection
« Odpověď #1 kdy: 08. 01. 2016, 11:14:09 »
Najdi si nejaku lopatu na upwork.com
Za par supov to budes mat hotove

none_

Re:parsovani dotazu - sql injection
« Odpověď #2 kdy: 08. 01. 2016, 13:33:17 »
No tim bych si nebyl tak jisty. Pokud chce zabezpecit metodu exec($query), ktera uz bere hotove sql se vsemi parametry uvnitr a nechce zasahovat do kodu okolo, tak to podle me nejde. Jak ma metoda exec vedet, ktera podminka je spravne a kde je tam podstrcena pro injection? Podle me jediny reseni je prepsat celou DAO vrstvu, aby pouzivala aspon metodu exec($query, $parameters) a pak se s tim da neco delat.

Kit

Re:parsovani dotazu - sql injection
« Odpověď #3 kdy: 08. 01. 2016, 13:49:00 »
Podle me jediny reseni je prepsat celou DAO vrstvu, aby pouzivala aspon metodu exec($query, $parameters) a pak se s tim da neco delat.

Správně je
Kód: [Vybrat]
$query->execute($parameters);
Skutečně je potřeba redesignovat celý přístup k databázi. Bezhlavě použít mysql_real_escape_string() nelze - také proto, že na číselné hodnoty se tato funkce nehodí.

none_

Re:parsovani dotazu - sql injection
« Odpověď #4 kdy: 08. 01. 2016, 14:00:09 »
Správně je
Kód: [Vybrat]
$query->execute($parameters);

Snazil jsem se naznacit to, ze jakmile predava parametry jako soucast hotoveho SQL, tak s tim nic neudela. Btw co to tvoje spravne reseni udela, kdyz jeho $query je String? Jeho interface prijima SQL retezec. Aby to opravil, musi ho zmenit na SQL retezec (prepared statement) + parametry. To jestli vevnitr pouzije k implementace nejakou tridu Query, ktera poskytuje metodu execute($parameters), je momentalne nepodstatne.


opio

Re:Parsování dotazu - SQL injection
« Odpověď #5 kdy: 08. 01. 2016, 14:41:17 »
jeste sem nasel greenSQL (proxy server), ale to bude nejaka heuristika asi.. musi se prepsat, diky za odpovedi

k

Re:Parsování dotazu - SQL injection
« Odpověď #6 kdy: 08. 01. 2016, 14:44:40 »
musime upravit metodu pres kterou jdou vsechny dotazy exec($query), tedy uvnitr parsovat SQL dotaz a zabezpecit.

To už je pozdě, validace a escapování se musí provést už při počátečním vkládání parametrů.
Standardně se to dělá $db->execsql('select a,b,c from table where a=:param', array('param'=>1)).
Prepared statement slouží na úplně jiné věci.

opio

Re:Parsování dotazu - SQL injection
« Odpověď #7 kdy: 08. 01. 2016, 14:55:42 »
prepared statement chapu jako predkompilovany dotaz, do ktereho se doplni parametry v okamziku spusteni.. tedy z principu je bezpecny a sql injection resi, protoze v okamziku kdy se do nej doplnuji parametry, dotaz uz je zkompilovany a nemuzu jej "dotvorit"

Karel

Re:Parsování dotazu - SQL injection
« Odpověď #8 kdy: 08. 01. 2016, 15:15:01 »
Ta WHERE podmínka už zkontrolovat nejde. Někdo se snaží riziko snížit tím, že v té podmínce něco zakáže. Například operátor OR. Útočník pak může přidat další podmínky, ale jen přes AND, takže vlastně data jen zúží. Ale i tak je to pro něj zajímavé, protože může například přidat tohle:
AND ((select 1 from users where username = 'admin' and password >= 'm') is not null)

Sadou takových dotazů se dá metodou binárního půlení číst data z jiných tabulek. A pokud zná databázovou strukturu, tak i mnohem efektivněji.

Pokud texty dotazů zná, tak možná dokáže přijít na to, jak tu podmínku oslabit i bez OR. Například:
WHERE username = 'pepa' AND user_access_level >= 4
.. a přidejte " *0 "

Uvádím to ani tak ne jako návod co udělat, jako spíše varování, že tohle stačit nebude.

k

Re:Parsování dotazu - SQL injection
« Odpověď #9 kdy: 08. 01. 2016, 15:26:05 »
prepared statement chapu jako predkompilovany dotaz, do ktereho se doplni parametry v okamziku spusteni.. tedy z principu je bezpecny a sql injection resi, protoze v okamziku kdy se do nej doplnuji parametry, dotaz uz je zkompilovany a nemuzu jej "dotvorit"

To chápeš správně, bohužel se tak neděje na klientu, ale na serveru, negativní důsledky jsou nabíledni.
Pokud se jeden dotaz vykonává jednou, escapuje se na klientovi, na server jde dotaz kompletní.

Kit

Re:Parsování dotazu - SQL injection
« Odpověď #10 kdy: 08. 01. 2016, 15:57:46 »
Někdo se snaží riziko snížit tím, že v té podmínce něco zakáže. Například operátor OR. Útočník pak může přidat další podmínky, ale jen přes AND, takže vlastně data jen zúží.

Tohle považuji za vtip.