NFsec Logo

io_uring jako kolejne wejście dla szkodliwego oprogramowania

Dzisiaj w Bezpieczeństwo Brak komentarzy.  (artykuł nr 932, ilość słów: 828)

I

o_uring jest stosunkowo nowym (wprowadzonym w marcu 2019 roku do jądra 5.1), wysoce wydajnym interfejsem do asynchronicznych operacji wejścia / wyjścia (I/O). Stał się odpowiedzią na brak dobrej i łatwej obsługi wielu jednoczesnych operacji I/O w systemie Linux. Jego zaletą jest możliwość pominięcia „kosztownych” wywołań systemowych (ang. syscalls). Zamiast tradycyjnego modelu, w którym aplikacja musi ciągle „pytać” jądro systemu o status swoich operacji (np. odczyt pliku) io_uring używa dwóch współdzielonych buforów pierścieniowych (stąd jego nazwa). Pierwszy z nich: Submission Queue (SQ) – to kolejka, do której aplikacja wrzuca zadania do wykonania przez jądro. Druga: Completion Queue (CQ) – to kolejna, w której jądro umieszcza wyniki zakończonych zadań. Dzięki temu aplikacja może wysłać całą serię zadań naraz i zostać poinformowana o ich zakończeniu, minimalizując kosztowne przełączanie kontekstu między trybem użytkownika (ang. user space), a trybem jądra (ang. kernel space).

Niestety interfejs ten zyskał złą sławę w kręgach bezpieczeństwa systemu Linux, ze względu na dużą liczbę podatności. Jednak ta wada nie stanowi o jego atrakcyjności dla rodziny złośliwego oprogramowania. Głównym powodem jest to, że io_uring pozwala na ominięcie tradycyjnych mechanizmów monitorowania bezpieczeństwa. Wiele narzędzi zabezpieczających systemy Linux (EDR/XDR) opiera swoje działanie na przechwytywaniu i analizowaniu wspomnianych wywołań systemowych. Standardowo, gdy program chce otworzyć plik, nawiązać połączenie sieciowe czy uruchomić inny proces, musi poprosić o to jądro za pomocą konkretnego wywołania systemowego (np. open(), connect(), execve()). Narzędzia bezpieczeństwa „nasłuchują” tych wywołań, aby analizować inicjujące je programy i wykrywać podejrzane zachowanie w łańcuchu wykonania. W tym momencie interfejs io_uring zmienia zasady gry. Operacje zgłoszone przez ten interfejs nie muszą generować żadnych, tradycyjnych wywołań systemowych dla każdej akcji. Złośliwe oprogramowanie może zacząć zlecać jądru wykonywanie operacji na plikach, czy gniazdach sieciowych, a narzędzia monitorujące po prostu tego nie zobaczą. Tworzy to swoisty „martwy punkt” dla podejrzanej aktywności w systemie.

W czerwcu 2022 roku Daniel Teixeira w swojej publikacji pt. Bypassing eBPF-based Security Enforcement Tools przedstawił koncepcję i demonstrację, jak można ominąć narzędzia monitorujące oparte o eBPF (ang. extended Berkeley Packet Filter). Była ona inspiracją dla rozwinięcia badań przez firmę ARMO (stojącą za Kubescape) i wypuszczenia w 2025 roku demonstracyjnego programu typu rootkit o nazwie Curing. Rootkit demonstruje komunikację między serwerem C2, a zainfekowanym hostem w celu pobierania poleceń i wykonywania ich bez wykonywania żadnych wywołań systemowych związanych z jego operacjami. Głównym celem było pokazanie, że interfejs io_uring umożliwia tak wiele operacji, że można na nim oprzeć działanie szkodliwego oprogramowania. Testy pokazały, że darmowe narzędzia typu: Falco oraz Tetragon były kompletnie ślepe, gdy ich konfiguracja skupiała się jedynie na monitorowaniu wywołań systemowych. Niestety, ze względu na zasady etycznego hackingu autorzy nie mogli przetestować ani opublikować wyników komercyjnych produktów. Podobne narzędzie, ale bardziej nastawione na działania ofensywne (Red Team) napisał Matheus Alves. RingReaper to prosty agent dla systemu Linux działający po fazie przełamania zabezpieczeń. Przeznaczony jest dla aktorów, którzy muszą działać w ukryciu, minimalizując ryzyko wykrycia przez rozwiązania typu EDR/XDR.

Obecnie wielu dostawców rozwiązań bezpieczeństwa dla systemu Linux przechodzi lub już posiada agenty oparte o mechanizm eBPF. Jednak jak pokazują powyższe przykłady – nie ma już gwarancji, że wywołania systemowe zostaną wykonane – samo podłączenie się do tego źródła danych może być niewystarczające. Potrzebne są hybrydowe rozwiązania, które będą posiadały dostęp do różnych struktur jądra. Fakt, że dostawcy bezpieczeństwa wykorzystali technologię stworzoną z myślą o śledzeniu i obserwowalności nie jest z natury wadliwe, ale sprowadza się do pewnych kosztów i ograniczeń. Dla eBPF nadzieję stanowi mechanizm o nazwie KRSI (ang. Kernel Runtime Security Instrumentation), który pojawił się od wersji 5.7 jądra. Umożliwia on wykorzystanie technologi eBPF do monitorowania zachowania systemu, wykrywania i blokowania ataków w czasie rzeczywistym poprzez przypinanie się do licznych punktów zaczepienia (ang. hooks) dostępnych w podsystemie LSM (ang. Linux Security Modules).

Należy jednak pamiętać, że sam io_uring nie stanowi automatycznego obejścia istniejących zabezpieczeń i założenia „peleryny niewidki”. Zanim dojdzie do wykorzystania tego interfejsu musi nastąpić kompromitacja systemu. Dlatego powszechne możliwości detekcji mogą mieć swoje zastosowanie przed tym etapem – tym bardziej, że sam io_uring nie obsługuje jeszcze w pełni wszystkich operacji i musi czasami być wspomagany „starymi” wywołaniami. Możemy też monitorować źródła wywołania io_uring_setup wymagane do zainicjowania interfejsu io_uring. W wielu środowiskach kontenerowych (np. Docker) profile bezpieczeństwa (seccomp) często domyślnie blokują wywołanie systemowe io_uring_setup, uniemożliwiając jego użycie, chyba że zostanie to wyraźnie dozwolone.

Więcej informacji: io_uring, io_uring Is Back, This Time as a Rootkit, Red Team Tactics: Evading EDR on Linux with io_uring, Kernel Runtime Security Instrumentation LSM+BPF=KRSI, io_uring: Linux Performance Boost or Security Headache?

Kategorie K a t e g o r i e : Bezpieczeństwo

Tagi T a g i : , , , , , , ,

Brak nowszych postów

Komentowanie tego wpisu jest zablokowane.