Fantasztikus sérülékenységek és hol találhatók meg (1. rész) - A webhelyek közötti parancsfájlok készítése a Django formai hibákkal

XSS parancsfájlok biztonsági rései

Miért továbbra is a webhelyek közötti szkriptek (XSS) a leggyakoribb web sebezhetőség? Az XSS azonosításának elmélete meglehetősen egyértelmű, sok statikus elemző eszköz készült az észlelésére, és mégis nagyon sok felfedezetlen sebezhetőség van. Szóval, mit ad?

Nos, az egyik ok az, hogy a hagyományos program-elemzési módszerek gyakran nem tudják azonosítani egy adott kóddarab szándékát. Például egy eszköz küzdhet azzal, hogy kitalálja, mely program objektumai tartalmazhatják a felhasználói bemeneteket.

Előző bejegyzésemben leírtam, hogy hogyan kezeljük ezt a problémát egy olyan rendszer felépítésével, amely több ezer nyílt forráskódú projekt biztonsági előírásait tanulja meg, és valódi sebezhetőségeket keres fel. Megígértem, hogy megoszt néhány jó példát is arról, amit megtanult.

Úgy döntöttem, hogy egy érdekes és meglehetősen váratlan forrásból indulok a Django-t használó projektekben felmerülő lehetséges kérdések. Ez a bejegyzés útmutató az XSS biztonsági réseinek azonosításához és kiaknázásához a Django űrlapokban található érvényesítési hibák felhasználásával. Ez egy valódi példa: https://github.com/mozilla/pontoon/pull/1175.

Ugorjunk egyenesen bele, és kezdjünk egy kis teszttel. Hányszor írt / látott kódot, amely hasonló a következő részlethez?

Mit szólsz ehhez?

Vagy ez?

Ezek mindegyike széles körű példa arra, hogy miként tudatja a felhasználót, hogy a megadott bemenet érvénytelen, igaz? A bemenetet a HTTP kérés paramétereiből veszik, és szépen nem formázják le a MyForm objektumba. Ha a mezők bármelyike ​​érvénytelen bemeneteket tartalmaz (például valaki beírja a "foobar" karakterláncot egy numerikus mezőbe), akkor a 400 Bad Request oldal visszatér a hiba leírásával. A kivonatok közötti különbség a visszaküldött hiba formátuma - HTML lista, egyszerű szöveg vagy JSON.

Egy millió dolláros kérdés - ezek közül a részletekből melyik teszi az Ön webes alkalmazásának XSS-alkalmazását?

Megválaszoljuk két szempontból a Django formák API-ját:

  1. Képes-e a támadó rosszindulatú adatokat beküldeni a felhasználó böngészőjében megjelenő weboldalra?
  2. Ezt a rosszindulatú adatot mindig megfelelően elkerülik, mielőtt visszajuttatják a felhasználónak?

A Django dokumentációja szerint a dinamikus hibaüzenetek a mező érvényesítési hibáinak elkészítéséhez a django.core.exmissions.ValidationError kivétel létrehozása a megfelelő üzenettel. Az űrlap bármely érvényesítési funkciójából (pl. A django.forms.BaseForm osztály clean () és clean_ () metódusokból kivont ilyen kivétel miatt az üzenet az űrlap hibaszótárában kerül tárolásra (django .forms.utils.ErrorDict), majd később esetleg megmutatják a felhasználónak.

Az ilyen kivételek kihasználásának egyik módja a beépített űrlapmezők használata, amelyek kényelmesen tükrözik a kivételüzenet hibás bevitelét. Kipróbáltam az összes itt felsorolt ​​Django űrlapmezőt, és a következő listát kaptam: ChoiceField, TypedChoiceField, MultipleChoiceField, FilePathField. Ezek mindegyike olyan hibaüzenetet generál, mint "Válasszon érvényes választást. A% (érték) s nem tartozik a rendelkezésre álló lehetőségek közé.", Ahol az érték a hibás bemenet. a győzelemhez .

A második lehetőség az egyedi mezők és / vagy érvényesítési eljárások kiaknázása. Például vegye figyelembe a következő kivonatot (egy valódi projektből vett és a rövidség érdekében módosítva):

A jó hasznos teher itt olyasmi, mint a foo. .

Igen, igazad van, önmagában a ValidationError kivételek nem adnak XSS-t. A megfelelő sebezhetőség érdekében még egy összetevőre van szükségünk - a hibaüzenetek befecskendezésének képességére a végső HTML oldalra, amely a felhasználónak visszatér.

A fent említett ErrorDict osztály a következő módszerekkel rendelkezik a hibaüzenetek kibontására:

  1. as_data () - nincs fertőtlenítés
  2. get_json_data (escape_html = hamis) - nincs fertőtlenítés, ha escape_html == hamis (alapértelmezett)
  3. as_json (escape_html = hamis) nincs fertőtlenítés, ha escape_html == hamis (alapértelmezett)
  4. as_ul () - biztonságos
  5. as_text () - nincs fertőtlenítés
  6. __str __ () (hívja as_ul ()) - biztonságos

Most térjünk vissza a kis kvízünkhöz. Könnyű belátni, hogy az 1. kivonat biztonságos, mert a __str __ () metódust használja, amely kiszabadítja a bemenetet. A 2. és 3. kivonat azonban veszélyes és XSS-t eredményezhet.

Két fő elvihető üzenet van itt. A fejlesztők számára a mantra „mindig tisztítsa meg a megbízhatatlan adatot”. Az egyik a biztonsági kutatók számára: egy egyszerű grep -R "ValidationError" kiszélesítheti a támadási felületet az Ön számára.

Mellesleg tiszteletem van, ha a kvíz helyes átadása a teljes üzenet elolvasása nélkül történt.

Web vagy mobilalkalmazás készítése?

A Crowdbotics az alkalmazás felgyorsításának, elindításának és méretezésének a leggyorsabb módja.

Fejlesztő? Próbálja ki a Crowdbotics App Builder alkalmazást, hogy gyorsan állványokat állítson fel és telepítsen számos népszerű kerettel.

Foglalt vagy nem műszaki? Csatlakozzon több száz boldog csapatépítő szoftverhez a Crowdbotics PM-kkel és szakértő fejlesztőkkel. A Crowdbotics által kezelt alkalmazásfejlesztés ingyenes ütemterve és költsége.