Około rok temu w DataLine uruchomiliśmy usługę do wykrywania i analizy luk w aplikacjach IT. Usługa oparta jest na rozwiązaniu chmurowym Qualys, o którym . Przez rok korzystania z tego rozwiązania przeprowadziliśmy 291 skanów dla różnych stron i zgromadziliśmy statystyki na temat najczęstszych luk w aplikacjach internetowych.
W poniższym artykule pokażę, jakie konkretnie luki w bezpieczeństwie ukrywają się za różnymi poziomami krytyczności. Zobaczymy, jakie luki skanery znajdowały szczególnie często, dlaczego mogą występować i jak się przed nimi chronić.

Qualys dzieli wszystkie luki w aplikacjach internetowych na trzy poziomy krytyczności: niski, średni i wysoki. Jeśli spojrzeć na rozkład według "ciężkości", wydaje się, że nie jest tak źle. Luki o wysokim poziomie krytyczności są nieliczne, głównie wszystko jest niekrytyczne:

Jednak luki niekrytyczne to nie to samo co bezpieczne. Mogą one również wyrządzić poważne szkody.
Najważniejsze "niekrytyczne" luki
- Luki związane z mieszanym zawartością.
Standardem bezpieczeństwa stron internetowych jest przesyłanie danych między klientem a serwerem za pomocą protokołu HTTPS, który wspiera szyfrowanie i chroni informacje przed przechwyceniem.
Niektóre strony korzystają z mieszanego zawartości: przesyłają część danych przez niezabezpieczony protokół HTTP. Częściej przesyłają zawartość pasywną - informacje, które wpływają tylko na wyświetlanie strony: zdjęcia, style css. Ale czasami przesyłane jest także zawartość aktywna: skrypty, które zarządzają zachowaniem strony. W takim przypadku za pomocą specjalnego oprogramowania można analizować przychodzącą z serwera informację z zawartością aktywną, modyfikować na bieżąco swoje odpowiedzi i zmuszać urządzenie do działania w sposób, w jaki nie zostało zaplanowane przez jego twórców.
Nowoczesne przeglądarki ostrzegają użytkowników, że strony z mieszanym zawartością są niebezpieczne i blokują taki content. Twórcy stron również otrzymują ostrzeżenia od przeglądarki w konsoli. Oto jak to wygląda w :

Czym to grozi: Oszuści wykorzystują niezabezpieczony protokół do przechwytywania informacji o użytkownikach, podmieniania skryptów i wysyłania zapytań do strony w imieniu użytkownika. Nawet jeśli odwiedzający stronę nie wprowadza danych, nie chroni go to przed phishingiem – wyciąganie poufnych informacji oszukańczymi metodami. Na przykład, za pomocą skryptu można przekierować użytkownika na niebezpieczną stronę, która maskuje się pod znaną użytkownikowi. W niektórych przypadkach złośliwa strona wygląda nawet lepiej niż oryginał, a użytkownik może samodzielnie wypełnić formularz i przekazać poufne dane.Co powinien pamiętać programista internetowy: Nawet jeśli administrator strony zainstalował i skonfigurował certyfikat SSL/TLS, luka może wystąpić z powodu czynnika ludzkiego. Na przykład, jeśli na którejkolwiek ze stron umieszczono link bezwzględny z http, zamiast względnego, i dodatkowo nie skonfigurowano przekierowań z http na https.
Wykrycie mieszanej zawartości na stronie można przeprowadzić za pomocą przeglądarki: można poszukać w kodzie źródłowym strony, sprawdzić powiadomienia w konsoli dewelopera. Jednak programista będzie musiał długo grzebać w kodzie. Proces można przyspieszyć za pomocą zautomatyzowanych narzędzi analitycznych, na przykład: , wolne oprogramowanie Lighthouse lub płatne oprogramowanie Screaming Frog SEO Spider.
Luka może również wystąpić z powodu problemów z kodem legacy – kodem, który został odziedziczony. Na przykład, jeśli część stron generowana jest na starym szablonie, który nie uwzględnia przechodzenia stron na https.
- Ciasteczka bez flag „HTTPOnly” i „secure”.
Atrybut „HTTPOnly” chroni ciasteczka przed przetwarzaniem przez skrypty, które oszuści wykorzystują do kradzieży danych użytkownika. Flaga „secure” nie pozwala na przesyłanie ciasteczek w otwartej postaci. Wymiana danych będzie dozwolona tylko w przypadku korzystania z zabezpieczonego protokołu HTTPS.
Oba atrybuty są zapisywane w właściwościach ciasteczek:
Set-Cookie: Secure; HttpOnlyCzym to grozi: Jeśli programista strony nie określił tych atrybutów, złośliwy użytkownik może przechwycić informacje użytkownika z ciasteczek i je wykorzystać. Jeśli ciasteczka są wykorzystywane do uwierzytelniania i autoryzacji, może on przejąć sesję użytkownika i działać na stronie w jego imieniu.
Co powinien pamiętać programista internetowy: Z reguły w popularnych frameworkach te atrybuty są ustawiane automatycznie. Mimo to sprawdź konfigurację serwera WWW i ustaw flagę: Set-Cookie HttpOnly; Secure.
Przy tym atrybut „HTTPOnly” uczyni ciasteczka niewidocznymi także dla twojego własnego JavaScript.
- Path-Based Vulnerabilities („ścieżkowe” luki).
Sk scanner informuje o takim zagrożeniu, jeśli znajdzie publicznie dostępną makro lub katalog strony z potencjalnie poufnymi informacjami. Na przykład wykrywa oddzielne pliki z konfiguracją systemu lub dostęp do całego systemu plików. Taka sytuacja może wystąpić, jeśli na stronie niewłaściwie ustawione są prawa dostępu.
Czym to grozi: Jeśli system plików "wystaje na zewnątrz", przestępczy może uzyskać dostęp do interfejsu systemu operacyjnego i próbować znaleźć katalogi z hasłami, jeśli są one przechowywane w jawnej formie (nie rób tego!). Lub można ukraść hashe haseł i próbować je złamać, a także spróbować podnieść uprawnienia w systemie i zagłębić się w infrastrukturę.
Co powinien pamiętać programista internetowy: Nie zapominaj o uprawnieniach i skonfiguruj platformę, serwer WWW, aplikację internetową, aby nie było możliwości "ucieczki" z katalogu webowego.
- Formularze do wprowadzania poufnych danych z włączoną funkcją autouzupełniania.
Jeśli użytkownik często wypełnia formularze na stronach, jego przeglądarka zapisuje te informacje za pomocą funkcji autouzupełniania.
Formularze na stronach mogą zawierać pola z poufnymi informacjami, takimi jak hasła lub numery kart kredytowych. Dla takich pól warto na stronie wyłączyć funkcję autouzupełniania formularzy.
Czym to grozi: Jeśli przeglądarka użytkownika zapisze poufne informacje, przestępca może je później przechwycić, na przykład za pomocą phishingu. W zasadzie, programista webowy, który zapomniał o tym szczególe, naraża swoich użytkowników.
Co powinien pamiętać programista internetowy: W tym przypadku mamy klasyczny konflikt: wygoda vs bezpieczeństwo. Jeśli programista webowy myśli o komforcie użytkownika, może świadomie wybrać autouzupełnianie. Na przykład, jeśli ważne jest przestrzeganie – zalecenia dotyczące dostępności treści dla użytkowników z ograniczeniami.
Dla większości przeglądarek można wyłączyć autouzupełnianie za pomocą atrybutu autocompete="off", na przykład:
<body> <form action="/pl/form/submit/" method="get" autocomplete="off" data-trp-original-action="/form/submit"> <div> <input type="text" placeholder="Imię"> </div> <div> <input type="text" id="lname" placeholder="Nazwisko" autocomplete="on"> </div> <div> <input type="number" placeholder="Numer karty kredytowej"> </div> <input type="submit"> <input type="hidden" name="trp-form-language" value="pl"/></form> </body>Jednak dla Chrome to nie zadziała. To obejście uzyskuje się za pomocą JavaScript, a wersję przepisu można znaleźć .
- W kodzie strony nie zdefiniowano nagłówka X-Frame-Options.
Ten nagłówek wpływa na tagi frame, iframe, embed lub object. Używając go, można całkowicie zabronić wbudowywania swojej strony w ramkę. W tym celu należy ustawić wartość X-Frame-Options: deny. Można też ustawić X-Frame-Options: sameorigin, wtedy wbudowywanie w iframe będzie dostępne tylko na twojej domenie.
Czym to grozi: Brak takiego nagłówka można wykorzystać na złośliwych stronach do clickjackingu. W takim ataku, haker tworzy przezroczystą ramkę nad przyciskami i oszukuje użytkownika. Na przykład: oszuści wstawiają do ramki na stronie elementy z mediów społecznościowych. Użytkownik uważa, że klika na przycisk na tej stronie. Zamiast tego kliknięcie jest przechwytywane i wysyłane jako zapytanie do serwisu społecznościowego, w którym użytkownik ma aktywną sesję. W ten sposób przestępcy rozsyłają spam w imieniu użytkownika lub sztucznie zwiększają liczbę subskrybentów oraz polubień.
Jeśli nie zabroni się takiej możliwości, haker może umieścić przycisk twojej aplikacji na złośliwej stronie. Może być zainteresowany twoim programem partnerskim lub twoimi użytkownikami.
Co powinien pamiętać programista internetowy: Podatność może wystąpić, jeśli X-Frame-Options z sprzeczną wartością jest ustawiane na serwerze www lub na równoważniku obciążeń. W takim przypadku serwer i równoważnik po prostu nadpiszą nagłówek, ponieważ mają wyższy priorytet w porównaniu do kodu backendowego.
Wartości deny i sameorigin nagłówka X-Frame-Options będą przeszkadzać w działaniu webwizora Yandexa. Aby umożliwić użycie iframe dla webwizora, należy napisać w ustawieniach osobną regułę. Na przykład, dla nginx można skonfigurować tak:
http{ ... map $http_referer $frame_options { "~webvisor.com" "ALLOW-FROM http://webvisor.com"; default "SAMEORIGIN"; } add_header X-Frame-Options $frame_options; ... } - Podatności PRSSI (import stylów względnych do ścieżki).
To jest podatność w stylach strony. Występuje, gdy do uzyskiwania plików stylów używane są względne linki typu href="/somefolder/styles.css/". Haker wykorzysta to, jeśli znajdzie sposób na przekierowanie użytkownika na złośliwą stronę. Strona wstawi względny link w swój adres URL i imituje odwołanie do stylów. Powstanie zapytanie o treści badsite.ru/…/somefolder/styles.css/, które pod przykrywką stylu może podejmować złośliwe działania.
Czym to grozi: Oszust będzie mógł skorzystać z tej luki, jeśli znajdzie kolejną słabość w zabezpieczeniach. W rezultacie można ukraść dane użytkownika z ciasteczek lub tokenów.
Co powinien pamiętać programista internetowy: Ustaw nagłówek X-Content-Type-Options: nosniff. W tym przypadku przeglądarka sprawdzi typ zawartości dla stylów. Jeśli typ odbiega od text/css, przeglądarka zablokuje żądanie.
Krytyczne luki
- Strona z polem dla hasła jest przesyłana z serwera przez niezabezpieczony kanał (HTML form containing password field(s) is served over HTTP).
Odpowiedź z serwera przez niezaszyfrowany kanał jest podatna na ataki typu „Man in the Middle”. Haker może przechwycić ruch i wślizgnąć się pomiędzy klientem a serwerem, gdy strona jest przesyłana z serwera do klienta.
Czym to grozi: Oszust będzie mógł podmienić stronę i wysłać użytkownikowi formularz danych osobowych, które trafią na serwer przestępcy.
Co powinien pamiętać programista internetowy: Niektóre strony zamiast hasła wysyłają użytkownikom jednorazowy kod na e-mail/telefon. W takim przypadku luka nie jest tak krytyczna, ale mechanizm utrudni życie użytkownikom.
- Wysłanie formularza z loginem i hasłem przez niezabezpieczony kanał (Login Form Is Not Submitted Via HTTPS).
W takim przypadku od użytkownika na serwer przez niezaszyfrowany kanał wysyłany jest formularz z loginem i hasłem.
Czym to grozi: W przeciwieństwie do poprzedniego przypadku, to już krytyczna luka. Przechwycenie poufnych danych jest prostsze, ponieważ nie trzeba nawet pisać kodu.
- Używanie bibliotek JavaScript z znanymi lukami.
W trakcie skanowania najczęściej używaną biblioteką stał się jQuery z szerokim zakresem wersji. W każdej z wersji jest co najmniej jedna, a czasem więcej znanych luk. Wpływ może być różny – zależy od natury luki.
Czym to grozi: Dla znanych luk istnieją exploity, na przykład takie:

Co powinien pamiętać programista internetowy: Regularnie wracaj do cyklu: wyszukiwanie znanych luk – usuwanie – sprawdzanie. Jeśli świadomie używasz przestarzałych bibliotek, na przykład w celu wsparcia starych przeglądarek lub z oszczędności budżetu, szukaj możliwości usunięcia znanej luki. - Złośliwe skrypty między witrynami (XSS).
Cross-Site Scripting (XSS), czyli skrypty międzystronowe, to ataki na aplikację internetową, w wyniku których w bazie danych pojawia się złośliwy kod. Jeśli Qualys wykryje taką lukę, oznacza to, że potencjalny napastnik może wprowadzić lub już wprowadził do kodu strony swój skrypt js w celu wykonania szkodliwych działań.XSS przechowywane (Stored XSS) są bardziej niebezpieczne, ponieważ skrypt jest wprowadzany na serwerze i wykonywany za każdym razem, gdy otworzona jest zaatakowana strona w przeglądarce.
XSS odzwierciedlone (Reflected XSS) są łatwiejsze do przeprowadzenia, ponieważ złośliwy skrypt można wprowadzić w żądaniu HTTP. Aplikacja otrzyma żądanie HTTP, nie zweryfikuje danych, zapakowuje je i natychmiast wysyła. Jeśli atakujący przechwyci ruch i wstawi skrypt w postaci
/*+coś+złego+*//to w imieniu klienta zostanie wysłane złośliwe żądanie.
Jasnym przykładem XSS są skrypty js, które imitują strony do wprowadzania CVC, daty ważności karty itp.
Co powinien pamiętać programista internetowy: W nagłówku Content-Security-Policy użyj atrybutu script-src, aby przeglądarka klienta ładowała i wykonywała tylko kod z zaufanego źródła. Na przykład, script-src 'self' dodaje do listy dozwolonych wszystkie skrypty tylko z naszej strony.
Najlepszą praktyką jest pozwolenie tylko na kod inline: zezwól na inline javascript za pomocą wartości unsafe-inline. Taka wartość pozwala na użycie inline js/css, ale nie zabrania podłączania plików js. W kombinacji ze script-src 'self' zabraniająszy wykonywania zewnętrznych skryptów.Zawsze loguj wszystko za pomocą report-uri i obserwuj próby wprowadzenia na stronę.
- SQL-iniekcje.
Luka ta oznacza możliwość wprowadzenia na stronę kodu SQL, który bezpośrednio odnosi się do bazy danych strony. SQL-iniekcja jest możliwa, jeśli dane od użytkownika nie są escapowane: nie są sprawdzane pod kątem poprawności i są natychmiast używane w zapytaniu. Na przykład, tak się dzieje, jeśli formularz na stronie nie sprawdza zgodności wprowadzonego typu danych.Czym to grozi: Jeśli napastnik wpisze w taki formularz zapytanie SQL, może zdewastować bazę danych lub ujawnić poufne informacje.
Co powinien pamiętać programista internetowy: Nie ufaj temu, co pochodzi z przeglądarki. Należy zabezpieczać się zarówno po stronie klienta, jak i serwera.
Po stronie klienta napisz walidację pól za pomocą JavaScript.
Wbudowane funkcje w popularnych frameworkach również pomagają w zabezpieczeniu podejrzanych znaków na serwerze. Na serwerze zaleca się również stosowanie parametryzowanych zapytań do baz danych.
Określ, gdzie dokładnie odbywa się interakcja z bazą danych w aplikacji webowej.
Interakcja występuje, gdy uzyskujemy jakiekolwiek informacje: zapytanie z id (zmiana id), utworzenie nowego użytkownika, nowy komentarz – nowe rekordy w bazie. Tutaj mogą wystąpić sql-iniekcje. Nawet przy usuwaniu rekordu z bazy możliwa jest sql-iniekcja.
Ogólne zalecenia
Nie wymyślaj koła na nowo – korzystaj z sprawdzonych frameworków. Zazwyczaj popularne frameworki są bardziej bezpieczne. Dla .NET to ASP.NET MVC i ASP.NET Core, dla Pythona – Django lub Flask, dla Rubiego – Ruby on Rails, dla PHP – Symfony, Laravel, Yii, dla JavaScript – Node.JS- Express.js, dla Java – Spring MVC.
Bądź na bieżąco z aktualizacjami od dostawcy i regularnie je aktualizuj. Wrażliwości zostaną odkryte, następnie napiszą exploit, opublikują go i wszystko zacznie się od nowa. Zapisz się na aktualizacje stabilnych wersji od dostawcy oprogramowania.
Sprawdzaj uprawnienia dostępu. Z perspektywy serwera zawsze odnosi się do swojego kodu tak, jakby był on całkowicie napisany przez twojego najgorszego wroga, który chce zburzyć twoją stronę i naruszyć integralność twoich danych. Tym bardziej, że czasami tak rzeczywiście jest.
Używaj klonów, środowisk testowych, a dopiero potem wprowadzaj zmiany w środowisku produkcyjnym. To pomoże, po pierwsze, uniknąć błędów i niedopatrzeń w środowisku produkcyjnym: środowisko produkcyjne przynosi zyski, a przestoje w produkcji są krytyczne. Przy dodawaniu, poprawianiu lub rozwiązywaniu jakiegokolwiek problemu warto przeprowadzać prace w środowisku testowym, następnie sprawdzać funkcjonalność i zidentyfikowane luki, a dopiero potem planować prace w środowisku produkcyjnym.
Chroń aplikację webową za pomocą i integrować z nim raporty z narzędzia skanującego luki. Na przykład w DataLine jako zestawienie usług używane są Qualys i FortiWeb.
Źródło: habr.com


