Problem na zamówienie (cz.1)

Czynnikiem podnoszącym ryzyko związane z aplikacjami jest ewolucja środowisk, w jakich są one eksploatowane. Kiedyś liczba osób, które miały dostęp do aplikacji (miały zainstalowanego klienta aplikacji i konto w aplikacji) lub środowiska (do serwera, sieci, klienta), była ograniczona, a więc również liczba potencjalnych intruzów (czy raczej miejsc, z których może działać intruz) była ograniczona. Dostęp można było kontrolować na wiele sposobów, np. dzięki zapewnieniu bezpieczeństwa fizycznego.

Obecnie sieci wielu oddziałów firmy są połączone w jeden organizm. Stacje robocze mogą korzystać nie tylko z zasobów wewnętrznych, ale także z Internetu. Przejęcie kontroli nad końcówką użytkownika, oprócz tego, że jest relatywnie proste, daje intruzowi możliwość działania "od wewnątrz". Większość firm bagatelizuje to ryzyko, sądząc, że jest ono niewielkie. Być może było to prawdą kilka lat temu, natomiast teraz - wraz z upowszechnieniem dostępu do Internetu z każdego stanowiska w firmie, tendencją do łączenia sieci oddziałowych w jedną sieć korporacyjną i znacznym postępem w technikach ataku właśnie na stacje robocze - ryzyko ataku z wewnątrz znacznie wzrosło.

Nieświadomi programiści

Zaskakująco dużo poważnych luk w zabezpieczeniach powstaje dlatego, że nikt nie przewidział możliwości ich powstania na etapie projektowania aplikacji, choć to akurat, przynajmniej w części, jest wynikiem braku świadomości zagrożeń po stronie zlecającego. Do tego dochodzą: brak wiedzy i brak czasu programistów, a także nieuwzględnianie bezpieczeństwa w testach.

Skupmy się na programistach. Ich edukacja nie obejmuje zazwyczaj bezpieczeństwa aplikacji, a jeśli już, to jest traktowana w sposób ogólny. Skąd to wynika? Na pewno z tego, że od programisty oczekuje się dziś zdolności do posługiwania się jak największą liczbą języków i narzędzi, by jak najszybciej móc wykonać projekt o określonej specyfice. Uczelnie nie traktują bezpieczeństwa priorytetowo.

Po wejściu na rynek pracy zaczyna się bieg za terminami i nie ma czasu, by zająć się bezpieczeństwem. Dodatkowym wzmocnieniem tej tendencji jest fakt, że klientom często nie można powiedzieć wprost, że cena, jaką płacą za oprogramowanie, nie uwzględnia testowania pod kątem bezpieczeństwa, lecz jedynie testy funkcjonalne. Tajemnicą poliszynela jest bowiem to, że o bezpieczeństwo dba się proporcjonalnie do skłonności klienta do zapłacenia za nie.

Większość programistów niskiego szczebla nie zdaje sobie sprawy, jakie skutki dla ogólnego poziomu bezpieczeństwa może mieć drobny błąd popełniony w kodzie pojedynczej procedury. Poza tym pokutuje opinia, że skoro nikt (poza autorami kodu) nie zna szczegółów implementacji, nie ma obaw o naruszenie bezpieczeństwa. Na nieszczęście ich klientów, to twierdzenie już od bardzo dawna nie jest prawdziwe. Przede wszystkim dlatego że najczęściej popełniane błędy można pogrupować w pewne klasy problemów i związane z nimi metody ataku. Niezorientowanym w temacie polecam listę OWASP Top 10, opisującą dziesięć najczęściej spotykanych błędów we współczesnych aplikacjach WWW .

Złych przykładów jest jednak dużo więcej. Problem złych praktyk stosowanych przez "szeregowych" programistów jest pogłębiany przez przykłady publikowane w podręcznikach programowania, dodawane do narzędzi, i przykłady znajdowane w Internecie. Przykłady, jak to przykłady, są zwykle bardzo uproszczone i przeważnie nie są pisane z uwzględnieniem praktyk bezpiecznego programowania. Problem w tym, że tego typu przykłady są często kopiowane bezpośrednio do kodu tworzonych aplikacji. Weźmy pod uwagę przykłady towarzyszące produktom Oracle:

Podstawowy przykład na temat Java Server Pages (JSP) "Hello World!" zawiera podatność typu cross-site scripting. Wiele innych przykładów, np. te pokazujące, jak wywoływać zapytania SQL ze skryptów JSP czy serwletów, umożliwia ataki metodą SQL-injection. Na tym nie koniec. W dokumentacji dotyczącej Oracle Single Sign-On jest przykład pokazujący, jak dostosowywać wygląd formularza logowania się. Przykład ten jest podatny na atak, którego rezultatem może być przejęcie haseł użytkowników korzystających z tego modułu.

Nie chcę przez to powiedzieć, że przykłady towarzyszące produktom Oracle są jakimś ewenementem, problem ten dotyczy bowiem w równym stopniu wielu innych producentów oprogramowania. Warto jednak zwrócić uwagę na to, że celem wymienionych przykładów nie jest edukowanie programisty w kierunku bezpieczeństwa, ale raczej pokazanie jak najprościej określonej funkcjonalności. Niestety - nieświadomy programista może takie same błędy popełniać (i niejednokrotnie popełnia!) później w swoim kodzie.

Błąd u podstaw

Przyczyną sprzyjającą powstawaniu błędów jest współczesny model tworzenia aplikacji. Często jeden zespół projektuje szkielet aplikacji za pomocą narzędzi do modelowania, inny zaś wypełnienia szkieletu kodem. Jeżeli żaden z tych zespołów nie ma w wymaganiach projektowych ustalonych reguł i dobrych praktyk dotyczących bezpieczeństwa, nie można liczyć na to, że kod będzie bezpieczny. Wymagania dotyczące bezpieczeństwa kodu należy formułować na wczesnym etapie projektowania aplikacji, żądać ich w fazie implementacji, a podczas testowania testować aplikacje pod kątem bezpieczeństwa.


TOP 200