Ramnit – dogłębna analiza

Data publikacji: 29/09/2017, Michał Praszmo

Ramnit rozpoczął swoją działalność w 2010 roku. Rozprzestrzeniał się wtedy głównie infekując pliki wykonywalne i dołączając się do plików HTML. Rok później ukazała się jego groźniejsza wersja – autor wykorzystał kod złośliwego oprogramowania Zeus, który wyciekł w 2011 r. Wykorzystanie elementów kodu Zeusa pozwoliło dodać do Ramnita nowe funkcje, które ostatecznie uczyniły go pełnoprawnym trojanem bankowym.

Obecnie Ramnit posiada dużo więcej funkcji:

    • Wykonywanie ataków Man-in-the-Browser
    • Wykradanie haseł FTP i ciasteczek z przeglądarek
    • Wykorzystywanie DGA (Domain Generation Algorithm) do znalezienia serwera C&C (Command and Control)
    • Ręczne dodawanie wyjątków w programach antywirusowych
    • Eskalacja uprawnień za pomocą podatności CVE-2013-3660 oraz CVE-2014-4113 (privilege escalation)
    • Wykonywanie zrzutów ekranów

    Pomimo zamknięcia trzystu serwerów C&C przez Europol w 2015, Ramnit nadal ma się dobrze. Ostatnio jest dystrybuowany za pomocą exploit-kita RIG EK z seamless gates.

    Działanie

    Główny plik wykonywalny jest spakowany w pewnego rodzaju matrioszce: pierwsza (wierzchnia) warstwa to autorskie pakowanie, z kolei druga to normalny UPX.

    path.png

    Pomimo tego, że plik binarny jest zaszyfrowany, odzyskanie oryginalnej formy nie jest względnie trudne. Wystarczy uruchomić program ładujący w debuggerze, ustawić breakpoint zaraz po wypakowaniu się kodu i wejść do nowo powstałej funkcji. breakpoint1.png

    Jeśli przeanalizujemy kod znajdujący się zaraz za końcem instrukcji odpowiedzialnych za załadowanie pliku wykonywalnego możemy łatwo zauważyć charakterystyczną sygnaturę formatu PE „MZ”:

    breakpoint2.png

    Po odszyfrowaniu pliku wykonywalnego i dekompresji UPX można zauważyć 3 główne funkcje:

    • ApplyExploit
    • CheckBypassed
    • start

    ApplyExploit

    W dużym skrócie jest to funkcja, której zadaniem jest sprawdzenie czy aktualnie zalogowany użytkownik jest administratorem i czy program posiada odpowiednio wysoki poziom Windows Integrity Level. W sytuacji, gdy uprawnienia są zbyt niskie, stara się je podnieść korzystając z CVE-2013-3660 (załatane w MS13-053) oraz CVE-2014-4113 (załatane w MS14-058). Przed uruchomieniem exploita złośliwe oprogramowanie sprawdza czy aktualizacje łatające te podatności są zainstalowane w systemie operacyjnym.

    Jeśli procesowi uda się uzyskać prawa administratora przechowuje wartość „TRUE” w kluczu rejestru HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\jfghdug_ooetvtgk.

    CheckBypassed

    W tej części kodu sprawdzane jest czy funkcji ApplyExploit udało się podnieść uprawnienia. Jeżeli wartość we wspomnianym wyżej kluczu rejestru nie została ustawiona, nadpisuje ją i uruchamia funkcję odpowiedzialną za dodanie wyjątków do Zapory sieciowej Windows.

    start

    Koordynuje działanie funkcji ApplyExploit i CheckBypassed. W przypadku udanego podniesienia poziomu uprawnień tworzy dwa procesy o nazwie „svchost.exe” i uruchamia w nich kod z bibliotek: modules.dll i rmnsoft.dll

    Funkcja CheckBypassed jest wykonywana przed ApplyExploit, więc aby program w pełni się wykonał, musi zostać wykonany drugi raz.

    dll_injects.png

    Konfiguracja statyczna

    Ramnit szyfruje komunikację z C&C za pomocą algorytmu RC4. Klucz wykorzystywany w komunikacji i identyfikator botnetu są dołączane do komunikatu w postaci zakodowanej z użyciem operacji XOR i stałego klucza osadzonego w próbce. Kodowanie pomija pierwszy znak klucza, a sam ciąg przetwarzany jest od końca.

    Kod:

    Wywołanie funkcji xor:

    Podawane w argumentach długości wiadomości są zazwyczaj za długie i musimy polegać na terminacji stringów nullbyte’ami:

    Konfiguracja DGA wydaje się być zawsze deklarowana na początku sekcji data datasection.png

    Mechanizm perzystencji

    Program kopiuje sam siebie do C:\Users\User\AppData\Roaming\Microsoft\Windows\Start Menu\Programs\Startup\.

    DGA

    Ramnit generuje listę potencjalnych domen C&C przy użyciu prostego generatora liczb pseudolosowych LCG (linear congruential generator):

    Generowanie domen:

    domain_gen.png

    Kod algorytmu DGA Ramnita zapisany w Pythonie:

    Komunikacja

    Ramnit komunikuje się z serwerami C&C przez port 443, nie używa jednak standardowego HTTPS, lecz swojego własnego protokołu:

    Struktura pakietu:

    Struktura danych zawartych w żądaniu:

    Jeśli więc chcemy wysłać własny pakiet z danymi musimy:

    • zaszyfrować dane większe niż 4 bajty z użyciem rc4 oraz klucza odzyskanego z xora
    • zapakować dane w chunki
    • połączyć wszystkie chunki razem
    • zapakować ostateczny bufor do pakietu

    Przykład ruchu sieciowego:

    403_traffic.png

    Niektóre rozpoznane komendy:

    Command Byte Value Description
    COMMAND_OK 0x01 Server’s response that the command executed successfully
    GET_DNSCHANGER 0x11 Get DNS-changer payload
    GET_INJECTS 0x13 Get web injects
    UPLOAD_COOKIES 0x15 Upload stolen cookies (zip format)
    GET_MODULE 0x21 Get a specific module
    GET_MODULE_LIST 0x23 Get a list of downloadable modules
    REGISTER_BOT 0xe2 Register bot (send 2 md5s)
    UPLOAD_INFO_GET_COMMANDS 0xe8 Upload detailed machine info

    Rejestracja jako bot

    Jeśli program chce się zarejestrować jako nowy bot wysyła rozkaz 0xe2 wraz z dwoma hashami md5 które bazują na strukturach:

    Implementacja w Pythonie:

    Jeśli rejestracja się powiodła i host zwrócił COMMAND_OK, bot wysyła pusty pakiet 0x51.

    Odpowiedź zawiera podpisaną wiadomość za której pomocą klient, korzystając ze zapisanego klucza publicznego może stwierdzić czy nikt się nie podszywa pod serwer.

    Moduły

    Ramnit może wysłać żądanie o listę dostępnych modułów i pobrać poszczególne indywidualnie:

    Antivirus Trusted Module v2.0

    Dodaje wyjątki do określonej listy antywirusów:

    Chrome reinstall module (x64-x86) v0.1

    Odinstalowuje Google Chrome

    I instaluje go ponownie:

    Cookie Grabber v0.2 (no mask)

    Kradnie ciasteczka z różnych lokalizacji systemowych i wysyła je spakowane w archiwum zip do C&C za pomocą rmnsoft.dll.

    Hooker

    Wykorzystywany do wykonywania ataków Man-in-the-Browser i podpinania się pod funkcje związane z HTTP.

    Webinjecty

    Webinjecty są stosunkowo nowym dodatkiem do Ramnita, korzystają jednak ze standardowego formatu używanego przez Zeusa:

    Obfuskacja / Unikanie detekcji

    Ramnit próbuje się ukryć przed Windows Defenderem dodając następujące wartości w rejestrze:

    Instrukcje NOP są dodawane w losowych miejscach. Utrudnia to m.in. stworzenie reguły Yara, która byłaby w stanie odnaleźć kluczowe fragmenty kodu.

    nop-fuscator.png

    Aktualizacja

    Podczas tworzenia tego artykułu natknęliśmy się na wariację Ramnita potocznie zwaną clickbideu. Program ładujący jest kompletnie inny, ale moduł służący do komunikacji (rmnsoft.dll) pozostał taki sam, z paroma małymi zmianami:

    DGA dodaje 3 różne TLD (Top-Level Domain) cyklicznie zamiast jednego:

    Zapis w Pythonie:

    Nowa wersja używa portu 8001 zamiast 443, zauważyliśmy również wersje korzystające z portu 442.

    Dodatkowo, inna wartość („fE4hNy1O”) jest wykorzystywana do wyliczenia drugiego skrótu md5

    Źródła

    IoCs

    Yara:

    Konfiguracje:

    Analizowane próbki

    sha256 loaderów:

    • d290225dde1b18bf68c4c42e06638a61fb336c91a2c4e6dd007bcbe7327fcbae
    • c2cae7d9ef91dfcc1ae8f542e0ac64ce66c526d5a4154241855020612d358ee8
    • 1f3fbca46a599b4f221ead7785606451365db45bbbc537ee0c4d019e8984d106
    • 9d723bb1dc375834ebb907271b83dffab44e98b82fa73da6267037f019e4bc83
    • f3567e2b5fc521987f0dd79aff6f3b1328db8e03fa825c3c030080a8b5819564
    • 7689465ba010537b0c29cf18d32a25962bd1605b717733f5953eb1b1eb0a68c9
    • f98ca50b7d07682ac359b97dd68eb924c4cbd825db72c1a132458e9bb765fa1e
    • 4b00b0ece480267af051e7907458381d8a9e8506c7da67b8a8e1d74d45773d68
    • 6ac47d82134385fa73386ff3cd7b2eb7008da2205b3f5af7b41fab45c63f9046
    • 6a1fc689d2ef32ee6288498f8a875c6dc880d7494f46c05d25d0e1f627984e8e
    • 522e935b91307b8c01e0ea8a724985f5b4e01227a761aeccb63b00f0d964f7e9
    • b3e67b5ee899c53f90c9da772592a4709372192542e1297bbce4929a8e1d5c69
    • 71d92cc6dc9273d162a969960b1021e5f18cf39b2c48043e5c5e49db5a58d955
    • da15c2a89334496910b6d966bf91fa25a1c9526c53796e06d166416abe7cf2f4
    • e4353bda9692581ea9743165dfd843238c23bb92e24b778983de80e90ac650a3

    sha256 modułów:

    • AvTrust:

      • b5a95a9bf419eab69d24b87ec561c657291d944acead30b25d004842db63338a
    • Chrome reinstall:

      • 862e690b2b24ed9f0394b88a6698f92ee6a3d2c511f76794a749611110cf9835
    • CookieGrabber:

      • 6e91c0cb5de7e8bdc5ad47581e07911424cfc784d38cd14dd9da0fa02fb0712c
    • FtpGrabber2:

      • 4a8c064fce1d8cf4017dc95c484fc058594d0e11cb6304cc5b3fed0561223514
    • Hooker:

      • a88151b3bf825e26ded28f94addeada095d2cd13791b2153a9594b26d9cfb85e
    • VNC IFSB:

      • b9cd5010f807caa133f133dad436cb7874d4433e36038c39537297b25efe7887

    domeny DGA (wygenerowane na podstawie seedów z sekcji Konfiguracje):