Skip to content

Latest commit

 

History

History
326 lines (266 loc) · 16.8 KB

File metadata and controls

326 lines (266 loc) · 16.8 KB

macOS Dyld Proces

Naučite hakovanje AWS-a od nule do heroja sa htARTE (HackTricks AWS Red Team Expert)!

Drugi načini podrške HackTricks-u:

Osnovne informacije

Pravi ulaz binarnog Mach-o fajla je dinamički linkovan, definisan u LC_LOAD_DYLINKER, obično je /usr/lib/dyld.

Ovaj linker će morati da locira sve izvršne biblioteke, mapira ih u memoriju i poveže sve ne-lenje biblioteke. Tek nakon ovog procesa, izvršiće se ulazna tačka binarnog fajla.

Naravno, dyld nema nikakve zavisnosti (koristi sistemske pozive i delove libSystem-a).

{% hint style="opasnost" %} Ako ovaj linker sadrži bilo kakvu ranjivost, budući da se izvršava pre izvršavanja bilo kog binarnog fajla (čak i visoko privilegovanih), bilo bi moguće eskalirati privilegije. {% endhint %}

Tok

Dyld će biti učitan preko dyldboostrap::start, koji će takođe učitati stvari poput stack canary-ja. To je zato što će ova funkcija primiti u svom apple argumentu ovu i druge osetljive vrednosti.

dyls::_main() je ulazna tačka dyld-a i njegov prvi zadatak je da pokrene configureProcessRestrictions(), što obično ograničava DYLD_* okružne promenljive objašnjene u:

{% content-ref url="./" %} . {% endcontent-ref %}

Zatim mapira dyld deljeni keš koji unapred povezuje sve važne sistem biblioteke, a zatim mapira biblioteke od kojih binarni fajl zavisi i nastavlja rekurzivno dok se ne učitaju sve potrebne biblioteke. Stoga:

  1. počinje sa učitavanjem ubačenih biblioteka sa DYLD_INSERT_LIBRARIES (ako je dozvoljeno)
  2. Zatim deljeni keširani
  3. Zatim uvežene
  4. Zatim nastavlja rekurzivno uvoziti biblioteke

Kada su sve učitane, pokreću se inicijalizatori ovih biblioteka. Oni su kodirani koristeći __attribute__((constructor)) definisane u LC_ROUTINES[_64] (sada zastarelo) ili preko pokazivača u odeljku označenom sa S_MOD_INIT_FUNC_POINTERS (obično: __DATA.__MOD_INIT_FUNC).

Terminatori su kodirani sa __attribute__((destructor)) i nalaze se u odeljku označenom sa S_MOD_TERM_FUNC_POINTERS (__DATA.__mod_term_func).

Stubovi

Svi binarni fajlovi na macOS-u su dinamički linkovani. Stoga, sadrže neke odeljke stubova koji pomažu binarnom fajlu da skoči na odgovarajući kod u različitim mašinama i kontekstima. Dyld je taj koji mora da reši ove adrese kada se binarni fajl izvrši (barem one koje nisu lenje).

Neki odeljci stubova u binarnom fajlu:

  • __TEXT.__[auth_]stubs: Pokazivači iz __DATA odeljaka
  • __TEXT.__stub_helper: Mali kod koji poziva dinamičko linkovanje sa informacijama o funkciji koju treba pozvati
  • __DATA.__[auth_]got: Globalna tabela offseta (adrese uvezenih funkcija, kada se reše, (vezuju se tokom vremena učitavanja jer je označena zastavicom S_NON_LAZY_SYMBOL_POINTERS)
  • __DATA.__nl_symbol_ptr: Pokazivači na ne-lenje simbole (vezuju se tokom vremena učitavanja jer je označena zastavicom S_NON_LAZY_SYMBOL_POINTERS)
  • __DATA.__la_symbol_ptr: Pokazivači na lenje simbole (vezuju se prilikom prvog pristupa)

{% hint style="upozorenje" %} Imajte na umu da pokazivači sa prefiksom "auth_" koriste jedan ključ za enkripciju u procesu kako bi ih zaštitili (PAC). Takođe, moguće je koristiti arm64 instrukciju BLRA[A/B] da proveri pokazivač pre nego što ga prati. I RETA[A/B] se može koristiti umesto adrese RET.
Zapravo, kod u __TEXT.__auth_stubs će koristiti braa umesto bl da pozove traženu funkciju kako bi autentifikovao pokazivač.

Takođe imajte na umu da trenutne verzije dyld-a učitavaju sve kao ne-lenje. {% endhint %}

Pronalaženje lenjih simbola

//gcc load.c -o load
#include <stdio.h>
int main (int argc, char **argv, char **envp, char **apple)
{
printf("Hi\n");
}

Interesantan deo disasemblera:

; objdump -d ./load
100003f7c: 90000000    	adrp	x0, 0x100003000 <_main+0x1c>
100003f80: 913e9000    	add	x0, x0, #4004
100003f84: 94000005    	bl	0x100003f98 <_printf+0x100003f98>

Moguće je videti da skok ka pozivu printf ide ka __TEXT.__stubs:

objdump --section-headers ./load

./load:	file format mach-o arm64

Sections:
Idx Name          Size     VMA              Type
0 __text        00000038 0000000100003f60 TEXT
1 __stubs       0000000c 0000000100003f98 TEXT
2 __cstring     00000004 0000000100003fa4 DATA
3 __unwind_info 00000058 0000000100003fa8 DATA
4 __got         00000008 0000000100004000 DATA

Prilikom rastavljanja __stubs odeljka:

objdump -d --section=__stubs ./load

./load:	file format mach-o arm64

Disassembly of section __TEXT,__stubs:

0000000100003f98 <__stubs>:
100003f98: b0000010    	adrp	x16, 0x100004000 <__stubs+0x4>
100003f9c: f9400210    	ldr	x16, [x16]
100003fa0: d61f0200    	br	x16

Možete videti da skočimo na adresu GOT-a, koja u ovom slučaju nije lenja i sadržaće adresu funkcije printf.

U drugim situacijama umesto direktnog skakanja na GOT, može se skočiti na __DATA.__la_symbol_ptr koji će učitati vrednost koja predstavlja funkciju koju pokušava da učita, zatim skočiti na __TEXT.__stub_helper koji skače na __DATA.__nl_symbol_ptr koji sadrži adresu dyld_stub_binder koji kao parametre uzima broj funkcije i adresu.
Ova poslednja funkcija, nakon što pronađe adresu tražene funkcije, upisuje je na odgovarajuće mesto u __TEXT.__stub_helper kako bi izbegla pretragu u budućnosti.

{% hint style="success" %} Međutim, primetite da trenutne verzije dyld-a sve učitavaju kao ne-lenje. {% endhint %}

Dyld opcode

Konačno, dyld_stub_binder mora pronaći naznačenu funkciju i upisati je na odgovarajuću adresu kako je ne bi ponovo tražio. Da bi to postigao, koristi opcode-ove (konačni automat) unutar dyld-a.

apple[] argument vektor

U macOS-u, glavna funkcija zapravo prima 4 argumenta umesto 3. Četvrti se zove apple i svaki unos je u obliku ključ=vrednost. Na primer:

// gcc apple.c -o apple
#include <stdio.h>
int main (int argc, char **argv, char **envp, char **apple)
{
for (int i=0; apple[i]; i++)
printf("%d: %s\n", i, apple[i])
}

macOS Dyld Process

macOS Biblioteka ubrizgavanje

Biblioteka ubrizgavanje je tehnika koja omogućava napadaču da ubaci zlonamernu biblioteku u proces kako bi dobio kontrolu nad izvršavanjem. Ova tehnika se često koristi za postizanje privilegija eskalacije ili za skrivanje zlonamernih aktivnosti. Dyld (dinamički linker) je odgovoran za učitavanje i povezivanje dinamičkih biblioteka u macOS operativnom sistemu. Napadač može iskoristiti ranjivosti u dyld procesu kako bi ubacio zlonamernu biblioteku i preuzeo kontrolu nad sistemom.

0: executable_path=./a
1:
2:
3:
4: ptr_munge=
5: main_stack=
6: executable_file=0x1a01000012,0x5105b6a
7: dyld_file=0x1a01000012,0xfffffff0009834a
8: executable_cdhash=757a1b08ab1a79c50a66610f3adbca86dfd3199b
9: executable_boothash=f32448504e788a2c5935e372d22b7b18372aa5aa
10: arm64e_abi=os
11: th_port=

{% hint style="success" %} Kada ove vrednosti stignu do glavne funkcije, osetljive informacije već su uklonjene iz njih ili bi došlo do curenja podataka. {% endhint %}

Moguće je videti sve ove interesantne vrednosti prilikom debagovanja pre ulaska u glavnu funkciju sa:

lldb ./apple

(lldb) target create "./a"
Trenutni izvršni fajl postavljen je na '/tmp/a' (arm64).
(lldb) process launch -s
[..]

(lldb) mem read $sp
0x16fdff510: 00 00 00 00 01 00 00 00 01 00 00 00 00 00 00 00  ................
0x16fdff520: d8 f6 df 6f 01 00 00 00 00 00 00 00 00 00 00 00  ...o............

(lldb) x/55s 0x016fdff6d8
[...]
0x16fdffd6a: "TERM_PROGRAM=WarpTerminal"
0x16fdffd84: "WARP_USE_SSH_WRAPPER=1"
0x16fdffd9b: "WARP_IS_LOCAL_SHELL_SESSION=1"
0x16fdffdb9: "SDKROOT=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX14.4.sdk"
0x16fdffe24: "NVM_DIR=/Users/carlospolop/.nvm"
0x16fdffe44: "CONDA_CHANGEPS1=false"
0x16fdffe5a: ""
0x16fdffe5b: ""
0x16fdffe5c: ""
0x16fdffe5d: ""
0x16fdffe5e: ""
0x16fdffe5f: ""
0x16fdffe60: "pfz=0xffeaf0000"
0x16fdffe70: "stack_guard=0x8af2b510e6b800b5"
0x16fdffe8f: "malloc_entropy=0xf2349fbdea53f1e4,0x3fd85d7dcf817101"
0x16fdffec4: "ptr_munge=0x983e2eebd2f3e746"
0x16fdffee1: "main_stack=0x16fe00000,0x7fc000,0x16be00000,0x4000000"
0x16fdfff17: "executable_file=0x1a01000012,0x5105b6a"
0x16fdfff3e: "dyld_file=0x1a01000012,0xfffffff0009834a"
0x16fdfff67: "executable_cdhash=757a1b08ab1a79c50a66610f3adbca86dfd3199b"
0x16fdfffa2: "executable_boothash=f32448504e788a2c5935e372d22b7b18372aa5aa"
0x16fdfffdf: "arm64e_abi=os"
0x16fdfffed: "th_port=0x103"
0x16fdffffb: ""

dyld_all_image_infos

Ovo je struktura izvezena od strane dyld-a sa informacijama o stanju dyld-a koje se može pronaći u izvornom kodu sa informacijama poput verzije, pokazivača na niz dyld_image_info, na dyld_image_notifier, da li je proces odvojen od deljenog keša, da li je inicijalizator libSystem-a pozvan, pokazivač na Mach zaglavlje dyld-a, pokazivač na verziju dyld-a...

dyld env promenljive

debug dyld

Interesantne env promenljive koje pomažu u razumevanju šta dyld radi:

  • DYLD_PRINT_LIBRARIES

Proverite svaku biblioteku koja je učitana:

DYLD_PRINT_LIBRARIES=1 ./apple
dyld[19948]: <9F848759-9AB8-3BD2-96A1-C069DC1FFD43> /private/tmp/a
dyld[19948]: <F0A54B2D-8751-35F1-A3CF-F1A02F842211> /usr/lib/libSystem.B.dylib
dyld[19948]: <C683623C-1FF6-3133-9E28-28672FDBA4D3> /usr/lib/system/libcache.dylib
dyld[19948]: <BFDF8F55-D3DC-3A92-B8A1-8EF165A56F1B> /usr/lib/system/libcommonCrypto.dylib
dyld[19948]: <B29A99B2-7ADE-3371-A774-B690BEC3C406> /usr/lib/system/libcompiler_rt.dylib
dyld[19948]: <65612C42-C5E4-3821-B71D-DDE620FB014C> /usr/lib/system/libcopyfile.dylib
dyld[19948]: <B3AC12C0-8ED6-35A2-86C6-0BFA55BFF333> /usr/lib/system/libcorecrypto.dylib
dyld[19948]: <8790BA20-19EC-3A36-8975-E34382D9747C> /usr/lib/system/libdispatch.dylib
dyld[19948]: <4BB77515-DBA8-3EDF-9AF7-3C9EAE959EA6> /usr/lib/system/libdyld.dylib
dyld[19948]: <F7CE9486-FFF5-3CB8-B26F-75811EF4283A> /usr/lib/system/libkeymgr.dylib
dyld[19948]: <1A7038EC-EE49-35AE-8A3C-C311083795FB> /usr/lib/system/libmacho.dylib
[...]
  • DYLD_PRINT_SEGMENTS

Proverite kako je svaka biblioteka učitana:

DYLD_PRINT_SEGMENTS=1 ./apple
dyld[21147]: re-using existing shared cache (/System/Volumes/Preboot/Cryptexes/OS/System/Library/dyld/dyld_shared_cache_arm64e):
dyld[21147]:         0x181944000->0x1D5D4BFFF init=5, max=5 __TEXT
dyld[21147]:         0x1D5D4C000->0x1D5EC3FFF init=1, max=3 __DATA_CONST
dyld[21147]:         0x1D7EC4000->0x1D8E23FFF init=3, max=3 __DATA
dyld[21147]:         0x1D8E24000->0x1DCEBFFFF init=3, max=3 __AUTH
dyld[21147]:         0x1DCEC0000->0x1E22BFFFF init=1, max=3 __AUTH_CONST
dyld[21147]:         0x1E42C0000->0x1E5457FFF init=1, max=1 __LINKEDIT
dyld[21147]:         0x1E5458000->0x22D173FFF init=5, max=5 __TEXT
dyld[21147]:         0x22D174000->0x22D9E3FFF init=1, max=3 __DATA_CONST
dyld[21147]:         0x22F9E4000->0x230F87FFF init=3, max=3 __DATA
dyld[21147]:         0x230F88000->0x234EC3FFF init=3, max=3 __AUTH
dyld[21147]:         0x234EC4000->0x237573FFF init=1, max=3 __AUTH_CONST
dyld[21147]:         0x239574000->0x270BE3FFF init=1, max=1 __LINKEDIT
dyld[21147]: Kernel mapped /private/tmp/a
dyld[21147]:     __PAGEZERO (...) 0x000000904000->0x000101208000
dyld[21147]:         __TEXT (r.x) 0x000100904000->0x000100908000
dyld[21147]:   __DATA_CONST (rw.) 0x000100908000->0x00010090C000
dyld[21147]:     __LINKEDIT (r..) 0x00010090C000->0x000100910000
dyld[21147]: Using mapping in dyld cache for /usr/lib/libSystem.B.dylib
dyld[21147]:         __TEXT (r.x) 0x00018E59D000->0x00018E59F000
dyld[21147]:   __DATA_CONST (rw.) 0x0001D5DFDB98->0x0001D5DFDBA8
dyld[21147]:   __AUTH_CONST (rw.) 0x0001DDE015A8->0x0001DDE01878
dyld[21147]:         __AUTH (rw.) 0x0001D9688650->0x0001D9688658
dyld[21147]:         __DATA (rw.) 0x0001D808AD60->0x0001D808AD68
dyld[21147]:     __LINKEDIT (r..) 0x000239574000->0x000270BE4000
dyld[21147]: Using mapping in dyld cache for /usr/lib/system/libcache.dylib
dyld[21147]:         __TEXT (r.x) 0x00018E597000->0x00018E59D000
dyld[21147]:   __DATA_CONST (rw.) 0x0001D5DFDAF0->0x0001D5DFDB98
dyld[21147]:   __AUTH_CONST (rw.) 0x0001DDE014D0->0x0001DDE015A8
dyld[21147]:     __LINKEDIT (r..) 0x000239574000->0x000270BE4000
[...]
  • DYLD_PRINT_INITIALIZERS

Štampajte kada se pokreće svaki inicijalizator biblioteke:

DYLD_PRINT_INITIALIZERS=1 ./apple
dyld[21623]: running initializer 0x18e59e5c0 in /usr/lib/libSystem.B.dylib
[...]

Ostali

  • DYLD_BIND_AT_LAUNCH: Lenje veze se rešavaju sa ne-lenjim vezama
  • DYLD_DISABLE_PREFETCH: Onemogućava preuzimanje __DATA i __LINKEDIT sadržaja
  • DYLD_FORCE_FLAT_NAMESPACE: Veze na jednom nivou
  • DYLD_[FRAMEWORK/LIBRARY]_PATH | DYLD_FALLBACK_[FRAMEWORK/LIBRARY]_PATH | DYLD_VERSIONED_[FRAMEWORK/LIBRARY]_PATH: Putanje za rešavanje
  • DYLD_INSERT_LIBRARIES: Učitava određenu biblioteku
  • DYLD_PRINT_TO_FILE: Piše dyld debug u fajl
  • DYLD_PRINT_APIS: Ispisuje pozive libdyld API-ja
  • DYLD_PRINT_APIS_APP: Ispisuje pozive libdyld API-ja napravljene od strane glavne aplikacije
  • DYLD_PRINT_BINDINGS: Ispisuje simbole kada su vezani
  • DYLD_WEAK_BINDINGS: Ispisuje samo slabe simbole kada su vezani
  • DYLD_PRINT_CODE_SIGNATURES: Ispisuje operacije registracije potpisa koda
  • DYLD_PRINT_DOFS: Ispisuje sekcije formata objekta D-Trace-a koje su učitane
  • DYLD_PRINT_ENV: Ispisuje okruženje viđeno od strane dyld-a
  • DYLD_PRINT_INTERPOSTING: Ispisuje operacije interpostovanja
  • DYLD_PRINT_LIBRARIES: Ispisuje učitane biblioteke
  • DYLD_PRINT_OPTS: Ispisuje opcije učitavanja
  • DYLD_REBASING: Ispisuje operacije relokacije simbola
  • DYLD_RPATHS: Ispisuje proširenja @rpath
  • DYLD_PRINT_SEGMENTS: Ispisuje mapiranja Mach-O segmenata
  • DYLD_PRINT_STATISTICS: Ispisuje statistiku vremena
  • DYLD_PRINT_STATISTICS_DETAILS: Ispisuje detaljnu statistiku vremena
  • DYLD_PRINT_WARNINGS: Ispisuje upozorenja
  • DYLD_SHARED_CACHE_DIR: Putanja za korišćenje keša deljenih biblioteka
  • DYLD_SHARED_REGION: "use", "private", "avoid"
  • DYLD_USE_CLOSURES: Omogućava zatvaranja

Moguće je pronaći više sa nečim poput:

strings /usr/lib/dyld | grep "^DYLD_" | sort -u

Ili preuzimanje dyld projekta sa https://opensource.apple.com/tarballs/dyld/dyld-852.2.tar.gz i pokretanje unutar foldera:

find . -type f | xargs grep strcmp| grep key,\ \" | cut -d'"' -f2 | sort -u

Reference

Naučite hakovanje AWS-a od nule do heroja sa htARTE (HackTricks AWS Red Team Expert)!

Drugi načini podrške HackTricks-u: