Zraniteľnosť root v jadre Linuxu a odmietnutie služby v systemd

Bezpečnostní výskumníci zo spoločnosti Qualys odhalili podrobnosti o dvoch zraniteľnostiach ovplyvňujúcich jadro Linuxu a správcu systému systemd. Zraniteľnosť v jadre (CVE-2021-33909) umožňuje lokálnemu používateľovi dosiahnuť spustenie kódu s právami root prostredníctvom manipulácie s vysoko vnorenými adresármi.

Nebezpečenstvo zraniteľnosti zvyšuje skutočnosť, že výskumníci boli schopní pripraviť pracovné exploity, ktoré fungujú na Ubuntu 20.04/20.10/21.04, Debian 11 a Fedora 34 v predvolenej konfigurácii. Treba poznamenať, že iné distribúcie neboli testované, ale teoreticky sú tiež náchylné na problém a môžu byť napadnuté. Úplný kód exploitov je prisľúbený, že bude zverejnený po odstránení problému všade, ale zatiaľ je k dispozícii iba prototyp obmedzenej funkčnosti, čo spôsobuje zlyhanie systému. Problém je prítomný od júla 2014 a ovplyvňuje vydania jadra od 3.16. Oprava zraniteľnosti bola koordinovaná s komunitou a prijatá do jadra 19. júla. Hlavné distribúcie už vygenerovali aktualizácie svojich balíčkov jadra (Debian, Ubuntu, Fedora, RHEL, SUSE, Arch).

Zraniteľnosť je spôsobená chybou pri kontrole výsledku konverzie size_t na int pred vykonaním operácií v kóde seq_file, ktorý vytvára súbory zo sekvencie záznamov. Zlyhanie pri kontrole môže viesť k prekročeniu hraníc zápisov do vyrovnávacej pamäte pri vytváraní, pripájaní a odstraňovaní veľmi vnorenej adresárovej štruktúry (veľkosť cesty väčšia ako 1 GB). Výsledkom je, že útočník môže dosiahnuť 10-bajtový reťazec "//deleted" zapísaný s posunom "-2 GB - 10 bajtov", ktorý ukazuje na oblasť bezprostredne pred pridelenou vyrovnávacou pamäťou.

Pripravený exploit vyžaduje na fungovanie 5 GB pamäte a 1 milión voľných inódov. Využívanie funguje tak, že volá mkdir() na vytvorenie hierarchie asi milióna podadresárov, aby sa dosiahla veľkosť cesty k súboru presahujúca 1 GB. Tento adresár je pripojený cez bind-mount v samostatnom užívateľskom mennom priestore, po ktorom sa spustí funkcia rmdir() na jeho odstránenie. Paralelne sa vytvorí vlákno, ktoré načíta malý program eBPF, ktorý sa zablokuje vo fáze po kontrole pseudokódu eBPF, ale pred jeho JIT kompiláciou.

V neprivilegovanom priestore názvov id užívateľa sa otvorí súbor /proc/self/mountinfo a načíta sa dlhý názov cesty adresára pripojeného k väzbe, výsledkom čoho je zapísanie reťazca "//deleted" do oblasti pred začiatkom vyrovnávacej pamäte. Pozícia pre zápis riadku je zvolená tak, aby prepísala inštrukciu v už testovanom, ale ešte neprekompilovanom programe eBPF.

Ďalej, na úrovni programu eBPF, sa nekontrolovaný zápis mimo vyrovnávacej pamäte transformuje na riadenú schopnosť čítať a zapisovať do iných štruktúr jadra prostredníctvom manipulácie so štruktúrami btf a map_push_elem. Výsledkom je, že exploit určí umiestnenie vyrovnávacej pamäte modprobe_path[] v pamäti jadra a prepíše v nej cestu „/sbin/modprobe“, čo vám umožní spustiť spustenie akéhokoľvek spustiteľného súboru s právami root v prípade request_module() volanie, ktoré sa vykoná napríklad pri vytváraní netlink socketu.

Výskumníci poskytujú niekoľko riešení, ktoré sú účinné len pre konkrétny exploit, ale neodstraňujú samotný problém. Odporúča sa nastaviť "/proc/sys/kernel/unprivileged_userns_clone" na 0, aby ste deaktivovali pripájacie adresáre v samostatnom mennom priestore ID užívateľa, a "/proc/sys/kernel/unprivileged_bpf_disabled" na 1, aby ste zakázali načítanie programov eBPF do jadra.

Je pozoruhodné, že pri analýze alternatívneho útoku, ktorý zahŕňa použitie mechanizmu FUSE namiesto bind-mound na pripojenie veľkého adresára, výskumníci narazili na ďalšiu zraniteľnosť (CVE-2021-33910), ktorá ovplyvňuje systémového manažéra systemd. Ukázalo sa, že pri pokuse o pripojenie adresára s veľkosťou cesty presahujúcou 8 MB cez FUSE proces inicializácie riadenia (PID1) vyčerpá pamäť zásobníka a spadne, čím sa systém dostane do „panického“ stavu.

Problém je v tom, že systemd sleduje a analyzuje obsah /proc/self/mountinfo a spracováva každý bod pripojenia vo funkcii unit_name_path_escape(), ktorá vykonáva operáciu strdupa(), ktorá umiestni údaje do zásobníka a nie do dynamicky pridelenej pamäte. . Keďže maximálna veľkosť zásobníka je obmedzená pomocou RLIMIT_STACK, spracovanie príliš veľkej cesty k bodu pripojenia spôsobí zlyhanie procesu PID1 a zastavenie systému. Na útok môžete použiť najjednoduchší modul FUSE v kombinácii s použitím vysoko vnoreného adresára ako bodu pripojenia, ktorého veľkosť cesty presahuje 8 MB.

Problém sa objavuje od systemd 220 (apríl 2015), už bol opravený v hlavnom repozitári systemd a opravený v distribúciách (Debian, Ubuntu, Fedora, RHEL, SUSE, Arch). Najmä vo vydaní systemd 248 exploit nefunguje kvôli chybe v kóde systemd, ktorá spôsobuje zlyhanie spracovania /proc/self/mountinfo. Je tiež zaujímavé, že v roku 2018 nastala podobná situácia a pri pokuse o napísanie exploitu pre zraniteľnosť CVE-2018-14634 v jadre Linuxu výskumníci Qualys narazili na tri kritické zraniteľnosti v systemd.

Zdroj: opennet.ru

Pridať komentár